Skip to content

Commit 9bf9594

Browse files
authored
Update msgIntel.js
Fixed bug related to --output arg.
1 parent a1ab612 commit 9bf9594

File tree

1 file changed

+93
-114
lines changed

1 file changed

+93
-114
lines changed

msgIntel.js

Lines changed: 93 additions & 114 deletions
Original file line numberDiff line numberDiff line change
@@ -9,17 +9,6 @@
99
ObjC.import('CoreServices');
1010

1111
// At the top level, after imports
12-
const OUTPUT_FORMAT = {
13-
LINE: '-line',
14-
JSON: '-json',
15-
CSV: '-csv',
16-
COLUMN: '-column',
17-
HTML: '-html',
18-
INSERT: '-insert',
19-
LIST: '-list'
20-
};
21-
22-
// Valid output formats as static array
2312
const VALID_OUTPUT_FORMATS = [
2413
'json', // Default
2514
'line',
@@ -50,7 +39,7 @@
5039

5140
// Add output format getter
5241
static get OUTPUT_FORMAT() {
53-
return OUTPUT_FORMAT;
42+
return VALID_OUTPUT_FORMATS;
5443
}
5544

5645
// Add valid formats getter
@@ -105,40 +94,14 @@
10594
return new Date(timestamp * 1000).toISOString();
10695
}
10796

108-
static formatOutput(data, format = OUTPUT_FORMAT.JSON) {
109-
// If not JSON format, return raw data as tab-delimited rows with headers
110-
if (format !== OUTPUT_FORMAT.JSON) {
111-
if (!data || !data.data || !data.data.messages) return '';
112-
113-
// Define headers
114-
const headers = [
115-
'GUID',
116-
'MESSAGE',
117-
'DATE',
118-
'SERVICE',
119-
'SENDER',
120-
'RECEIVER'
121-
].join('\t');
122-
123-
// Format data rows
124-
const rows = data.data.messages.map(msg => {
125-
const m = msg.message;
126-
return [
127-
m.guid,
128-
m.content.text,
129-
m.timestamps.date,
130-
m.communication.channel.service,
131-
m.communication.sender.phone_number || m.communication.sender.email || '',
132-
m.communication.receiver.phone_number || m.communication.receiver.email || ''
133-
].join('\t');
134-
});
135-
136-
// Combine headers and rows
137-
return [headers, ...rows].join('\n');
97+
static formatOutput(data, format = 'json') {
98+
// Default to JSON
99+
if (!format || format === 'json') {
100+
return JSON.stringify(data, null, 2);
138101
}
139-
140-
// Return formatted JSON
141-
return JSON.stringify(data, null, 2);
102+
103+
// Otherwise pass format directly to sqlite
104+
return data;
142105
}
143106
}
144107

@@ -192,11 +155,13 @@
192155
this.pipe = $.NSPipe.pipe;
193156
}
194157

195-
query(sql, format = OUTPUT_FORMAT.JSON) {
158+
query(sql, format = 'json') {
196159
try {
197160
const task = $.NSTask.alloc.init;
198161
task.launchPath = MsgIntelUtils.SQLITE_BIN;
199-
task.arguments = [this.dbPath, format, sql];
162+
163+
// Pass format directly to sqlite
164+
task.arguments = [this.dbPath, `-${format}`, sql];
200165

201166
const pipe = $.NSPipe.pipe;
202167
task.standardOutput = pipe;
@@ -206,7 +171,8 @@
206171
const data = pipe.fileHandleForReading.readDataToEndOfFile;
207172
const output = $.NSString.alloc.initWithDataEncoding(data, $.NSUTF8StringEncoding).js;
208173

209-
return format === OUTPUT_FORMAT.JSON ? JSON.parse(output) : output;
174+
// Only parse if JSON
175+
return format === 'json' ? JSON.parse(output) : output;
210176
} catch(e) {
211177
return null;
212178
}
@@ -231,7 +197,7 @@
231197
};
232198
}
233199

234-
getMessages(format = OUTPUT_FORMAT.JSON) {
200+
getMessages(format = 'json') {
235201
const sql = `SELECT
236202
m.ROWID, m.guid, m.text, m.service, m.handle_id,
237203
m.is_from_me, m.destination_caller_id,
@@ -250,15 +216,14 @@
250216
LEFT JOIN chat c ON cmj.chat_id = c.ROWID
251217
WHERE m.text IS NOT NULL;`;
252218

253-
const results = this.query(sql);
254-
255-
if (format !== OUTPUT_FORMAT.JSON) {
256-
return results;
257-
}
219+
// For non-JSON formats, return raw sqlite output
220+
if (format !== 'json') {
221+
return this.query(sql, format);
222+
}
258223

259-
if (!results) return [];
224+
const messages = this.query(sql);
225+
if (!messages) return { data: { messages: [] }};
260226

261-
262227
return {
263228
job: {
264229
job_id: `JOB-${$.NSProcessInfo.processInfo.processIdentifier}`,
@@ -275,7 +240,7 @@
275240
}
276241
},
277242
data: {
278-
messages: results ? results.map(msg => ({
243+
messages: messages.map(msg => ({
279244
message: {
280245
guid: msg.guid,
281246
timestamps: {
@@ -356,7 +321,7 @@
356321
ck_record_change_tag: msg.ck_record_change_tag
357322
}
358323
}
359-
})) : []
324+
}))
360325
}
361326
};
362327
}
@@ -388,7 +353,7 @@
388353
};
389354
}
390355

391-
getAttachments(format = OUTPUT_FORMAT.JSON) {
356+
getAttachments(format = 'json') {
392357
const sql = `SELECT
393358
a.ROWID,
394359
a.guid,
@@ -421,13 +386,13 @@
421386
LEFT JOIN message m ON maj.message_id = m.ROWID
422387
ORDER BY a.ROWID ASC;`;
423388

424-
const results = this.query(sql, format);
425-
426-
if (format !== OUTPUT_FORMAT.JSON) {
427-
return results;
389+
// For non-JSON formats, return raw sqlite output
390+
if (format !== 'json') {
391+
return this.query(sql, format);
428392
}
429393

430-
if (!results) return [];
394+
const attachments = this.query(sql);
395+
if (!attachments) return { data: { attachments: [] }};
431396

432397
return {
433398
job: {
@@ -444,41 +409,43 @@
444409
type: "discover"
445410
}
446411
},
447-
attachments: results.map(att => ({
448-
attachment: {
449-
guid: att.guid,
450-
created_date: MsgIntelUtils.convertAppleDate(att.created_date),
451-
metadata: {
452-
filename: att.filename,
453-
mime_type: att.mime_type,
454-
uti: att.uti,
455-
transfer_name: att.transfer_name,
456-
total_bytes: att.total_bytes
457-
},
458-
status: {
459-
transfer_state: att.transfer_state,
460-
is_outgoing: att.is_outgoing,
461-
is_sticker: att.is_sticker,
462-
hide_attachment: att.hide_attachment,
463-
is_commsafety_sensitive: att.is_commsafety_sensitive,
464-
ck_sync_state: att.ck_sync_state
465-
},
466-
message: {
467-
guid: att.guid.substring(att.guid.indexOf('_', att.guid.indexOf('_') + 1) + 1),
468-
is_from_me: att.is_from_me,
469-
communication: MsgIntelUtils.mapCommunication(att,
470-
this.handles.byRowId.get(att.handle_id),
471-
this.handles.byId.get(att.destination_caller_id)),
472-
state: {
473-
is_delivered: Boolean(att.is_delivered),
474-
is_read: Boolean(att.is_read),
475-
is_sent: Boolean(att.is_sent),
476-
is_spam: Boolean(att.is_spam),
477-
is_kt_verified: Boolean(att.is_kt_verified)
412+
data: {
413+
attachments: attachments.map(att => ({
414+
attachment: {
415+
guid: att.guid,
416+
created_date: MsgIntelUtils.convertAppleDate(att.created_date),
417+
metadata: {
418+
filename: att.filename,
419+
mime_type: att.mime_type,
420+
uti: att.uti,
421+
transfer_name: att.transfer_name,
422+
total_bytes: att.total_bytes
423+
},
424+
status: {
425+
transfer_state: att.transfer_state,
426+
is_outgoing: att.is_outgoing,
427+
is_sticker: att.is_sticker,
428+
hide_attachment: att.hide_attachment,
429+
is_commsafety_sensitive: att.is_commsafety_sensitive,
430+
ck_sync_state: att.ck_sync_state
431+
},
432+
message: {
433+
guid: att.guid.substring(att.guid.indexOf('_', att.guid.indexOf('_') + 1) + 1),
434+
is_from_me: att.is_from_me,
435+
communication: MsgIntelUtils.mapCommunication(att,
436+
this.handles.byRowId.get(att.handle_id),
437+
this.handles.byId.get(att.destination_caller_id)),
438+
state: {
439+
is_delivered: Boolean(att.is_delivered),
440+
is_read: Boolean(att.is_read),
441+
is_sent: Boolean(att.is_sent),
442+
is_spam: Boolean(att.is_spam),
443+
is_kt_verified: Boolean(att.is_kt_verified)
444+
}
478445
}
479446
}
480-
}
481-
}))
447+
}))
448+
}
482449
};
483450
}
484451
}
@@ -499,7 +466,7 @@
499466
};
500467
}
501468

502-
searchAll(inputStr, format = OUTPUT_FORMAT.JSON) {
469+
searchAll(inputStr, format = 'json') {
503470
const escapedInputStr = inputStr.replace(/_/g, '\\_').replace(/%/g, '\\%');
504471

505472
const msgSql = `SELECT
@@ -524,9 +491,15 @@
524491
OR h.id LIKE '%${escapedInputStr}%'
525492
OR m.destination_caller_id LIKE '%${escapedInputStr}%';`;
526493

494+
// For non-JSON formats, return raw sqlite output
495+
if (format !== 'json') {
496+
return this.query(msgSql, format);
497+
}
498+
527499
const messages = this.query(msgSql);
500+
if (!messages) return { data: { messages: [] }};
528501

529-
const output = {
502+
return {
530503
job: {
531504
job_id: `JOB-${$.NSProcessInfo.processInfo.processIdentifier}`,
532505
user: MsgIntelUtils.USER_INFO.username,
@@ -627,8 +600,6 @@
627600
}))
628601
}
629602
};
630-
631-
return MsgIntelUtils.formatOutput(output, format);
632603
}
633604

634605
searchByDate(startDate, endDate) {
@@ -806,7 +777,7 @@
806777
};
807778
}
808779

809-
getHiddenMessages(format = OUTPUT_FORMAT.JSON) {
780+
getHiddenMessages(format = 'json') {
810781
const sql = `SELECT
811782
-- Timeline Context
812783
crm.delete_date,
@@ -841,12 +812,14 @@
841812
WHERE m.text IS NOT NULL
842813
ORDER BY crm.delete_date DESC;`;
843814

844-
const results = this.query(sql, format);
845-
846-
if (format !== OUTPUT_FORMAT.JSON) {
847-
return results;
815+
// For non-JSON formats, return raw sqlite output
816+
if (format !== 'json') {
817+
return this.query(sql, format);
848818
}
849819

820+
const messages = this.query(sql);
821+
if (!messages) return { data: { hidden_messages: [] }};
822+
850823
return {
851824
job: {
852825
job_id: `JOB-${$.NSProcessInfo.processInfo.processIdentifier}`,
@@ -863,7 +836,7 @@
863836
}
864837
},
865838
data: {
866-
hidden_messages: results.map(msg => ({
839+
hidden_messages: messages.map(msg => ({
867840
message: {
868841
guid: msg.guid,
869842
is_from_me: msg.is_from_me,
@@ -912,7 +885,7 @@
912885
};
913886
}
914887

915-
getContacts(format = OUTPUT_FORMAT.JSON) {
888+
getContacts(format = 'json') {
916889
const sql = `
917890
SELECT
918891
h.ROWID,
@@ -943,9 +916,9 @@
943916
GROUP BY h.ROWID
944917
ORDER BY h.id;`;
945918

946-
const results = this.query(sql, OUTPUT_FORMAT.JSON);
919+
const results = this.query(sql, format);
947920

948-
if (OUTPUT_FORMAT.JSON !== OUTPUT_FORMAT.JSON) {
921+
if (format !== 'json') {
949922
return results;
950923
}
951924

@@ -1105,7 +1078,7 @@ Options:
11051078
// Main execution
11061079
if (typeof $ !== 'undefined') {
11071080
const options = parseArgs();
1108-
const format = options.output || OUTPUT_FORMAT.JSON;
1081+
const format = options.output || 'json';
11091082

11101083
// Add drafts handler
11111084
if (options.drafts) {
@@ -1126,7 +1099,13 @@ Options:
11261099

11271100
if (options.search) {
11281101
const searchResults = search.searchAll(options.search, format);
1129-
console.log(searchResults);
1102+
// For non-JSON formats, return raw output
1103+
if (format !== 'json') {
1104+
console.log(searchResults);
1105+
} else {
1106+
// For JSON (default), stringify the results
1107+
console.log(JSON.stringify(searchResults, null, 2));
1108+
}
11301109
return;
11311110
}
11321111

@@ -1152,7 +1131,7 @@ Options:
11521131
}
11531132
};
11541133

1155-
if (format !== OUTPUT_FORMAT.JSON) {
1134+
if (format !== VALID_OUTPUT_FORMATS[0]) {
11561135
let result = '';
11571136
for (const [key, value] of Object.entries(results.data)) {
11581137
if (value) result += value + '\n';
@@ -1167,7 +1146,7 @@ Options:
11671146
if (options.hidden) {
11681147
const hidden = new HiddenMessages();
11691148
const results = hidden.getHiddenMessages(format);
1170-
if (format !== OUTPUT_FORMAT.JSON) {
1149+
if (format !== VALID_OUTPUT_FORMATS[0]) {
11711150
console.log(results);
11721151
} else {
11731152
console.log(JSON.stringify(results, null, 2));

0 commit comments

Comments
 (0)