feat: add option to refresh mutual friends data for individual nodes in the graph context menu

This commit is contained in:
pa
2026-03-25 22:05:18 +09:00
parent a811100038
commit 6b728951fa
5 changed files with 317 additions and 61 deletions

View File

@@ -38,11 +38,16 @@ const mutualGraph = {
}
const friendTable = `${dbVars.userPrefix}_mutual_graph_friends`;
const linkTable = `${dbVars.userPrefix}_mutual_graph_links`;
const metaTable = `${dbVars.userPrefix}_mutual_graph_meta`;
const pairs = entries instanceof Map ? entries : new Map();
await sqliteService.executeNonQuery('BEGIN');
try {
await sqliteService.executeNonQuery(`DELETE FROM ${friendTable}`);
await sqliteService.executeNonQuery(`DELETE FROM ${linkTable}`);
await sqliteService.executeNonQuery(
`DELETE FROM ${linkTable} WHERE friend_id NOT IN (SELECT friend_id FROM ${metaTable} WHERE opted_out = 1)`
);
await sqliteService.executeNonQuery(
`DELETE FROM ${friendTable} WHERE friend_id NOT IN (SELECT friend_id FROM ${metaTable} WHERE opted_out = 1)`
);
if (pairs.size === 0) {
await sqliteService.executeNonQuery('COMMIT');
return;
@@ -131,6 +136,61 @@ const mutualGraph = {
}
}, `SELECT mutual_id, COUNT(*) FROM ${linkTable} GROUP BY mutual_id`);
return mutualCountMap;
},
async upsertMutualGraphMeta(friendId, { lastFetchedAt, optedOut }) {
if (!dbVars.userPrefix || !friendId) {
return;
}
const metaTable = `${dbVars.userPrefix}_mutual_graph_meta`;
const escapedId = friendId.replace(/'/g, "''");
const time = (lastFetchedAt || new Date().toISOString()).replace(
/'/g,
"''"
);
const optedOutInt = optedOut ? 1 : 0;
await sqliteService.executeNonQuery(
`INSERT OR REPLACE INTO ${metaTable} (friend_id, last_fetched_at, opted_out) VALUES ('${escapedId}', '${time}', ${optedOutInt})`
);
},
async bulkUpsertMutualGraphMeta(entries) {
if (!dbVars.userPrefix || !entries || entries.size === 0) {
return;
}
const metaTable = `${dbVars.userPrefix}_mutual_graph_meta`;
let values = '';
const now = new Date().toISOString();
entries.forEach(({ optedOut }, friendId) => {
if (!friendId) return;
const escapedId = friendId.replace(/'/g, "''");
const optedOutInt = optedOut ? 1 : 0;
values += `('${escapedId}', '${now}', ${optedOutInt}),`;
});
if (values) {
values = values.slice(0, -1);
await sqliteService.executeNonQuery(
`INSERT OR REPLACE INTO ${metaTable} (friend_id, last_fetched_at, opted_out) VALUES ${values}`
);
}
},
async getMutualGraphMeta() {
const metaMap = new Map();
if (!dbVars.userPrefix) {
return metaMap;
}
const metaTable = `${dbVars.userPrefix}_mutual_graph_meta`;
await sqliteService.execute((dbRow) => {
const friendId = dbRow[0];
if (friendId) {
metaMap.set(friendId, {
lastFetchedAt: dbRow[1] || null,
optedOut: dbRow[2] === 1
});
}
}, `SELECT friend_id, last_fetched_at, opted_out FROM ${metaTable}`);
return metaMap;
}
};