async function process_message(whoami, collection, message, kind, parent) { let content = JSON.parse(message.content); if (typeof content == 'string') { let x; for (let id of whoami || []) { x = await ssb.privateMessageDecrypt(id, content); if (x) { try { content = JSON.parse(x); content.draft = true; break; } catch { return; } } } if (!x) { return; } if (content.type !== kind || (parent && content.parent !== parent)) { return; } } else { content.draft = false; } if (content?.key) { if (content?.tombstone) { delete collection[content.key]; } else { collection[content.key] = Object.assign( collection[content.key] || {}, content ); } } else { collection[message.id] = Object.assign(content, {id: message.id}); if (!collection[message.id].editors) { collection[message.id].editors = [message.author]; } } return true; } let g_new_message_resolve; let g_new_message_promise = new Promise(function (resolve, reject) { g_new_message_resolve = resolve; }); function new_message() { return g_new_message_promise; } core.register('onMessage', function (id) { let resolve = g_new_message_resolve; g_new_message_promise = new Promise(function (resolve, reject) { g_new_message_resolve = resolve; }); if (resolve) { resolve(); } }); export async function collection( ids, kind, parent, max_rowid, data, include_private ) { let whoami = await ssb.getIdentities(); data = data ?? {}; let rowid = 0; let first = true; await ssb.sqlAsync( 'SELECT MAX(rowid) AS rowid FROM messages', [], function (row) { rowid = row.rowid; } ); while (true) { if (rowid == max_rowid) { await new_message(); await ssb.sqlAsync( 'SELECT MAX(rowid) AS rowid FROM messages', [], function (row) { rowid = row.rowid; } ); first = false; } let modified = false; let rows = []; await ssb.sqlAsync( ` SELECT messages.id, author, json(content) AS content, timestamp FROM messages JOIN json_each(?1) AS id ON messages.author = id.value WHERE messages.rowid > ?2 AND messages.rowid <= ?3 AND ((json_extract(messages.content, '$.type') = ?4 AND (?5 IS NULL OR json_extract(messages.content, '$.parent') = ?5)) OR (?6 AND content LIKE '"%')) ORDER BY timestamp `, [ JSON.stringify(ids), max_rowid ?? -1, rowid, kind, parent, include_private ? true : false, ], function (row) { rows.push(row); } ); max_rowid = rowid; for (let row of rows) { if (await process_message(whoami, data, row, kind, parent)) { modified = true; } } if (first || modified) { break; } } return [rowid, data]; }