refactor: inbox announce(delete) handling to also handle context deletion, #13712

This commit is contained in:
Julian Lam
2025-10-16 11:27:21 -04:00
parent 4d5005b972
commit 2b2028e446
2 changed files with 28 additions and 10 deletions

View File

@@ -81,6 +81,10 @@ Contexts.getItems = async (uid, id, options) => {
} }
if (items) { if (items) {
if (options.returnRootId) {
return items.pop();
}
items = await Promise.all(items items = await Promise.all(items
.map(async item => (activitypub.helpers.isUri(item) ? parseString(uid, item) : parseItem(uid, item)))); .map(async item => (activitypub.helpers.isUri(item) ? parseString(uid, item) : parseItem(uid, item))));
items = items.filter(Boolean); items = items.filter(Boolean);

View File

@@ -188,14 +188,14 @@ inbox.delete = async (req) => {
throw new Error('[[error:invalid-pid]]'); throw new Error('[[error:invalid-pid]]');
} }
} }
const pid = object.id || object; const id = object.id || object;
let type = object.type || undefined; let type = object.type || undefined;
// Deletes don't have their objects resolved automatically // Deletes don't have their objects resolved automatically
let method = 'purge'; let method = 'purge';
try { try {
if (!type) { if (!type) {
({ type } = await activitypub.get('uid', 0, pid)); ({ type } = await activitypub.get('uid', 0, id));
} }
if (type === 'Tombstone') { if (type === 'Tombstone') {
@@ -208,27 +208,41 @@ inbox.delete = async (req) => {
// Deletions must be made by an actor of the same origin // Deletions must be made by an actor of the same origin
const actorHostname = new URL(actor).hostname; const actorHostname = new URL(actor).hostname;
const objectHostname = new URL(pid).hostname; const objectHostname = new URL(id).hostname;
if (actorHostname !== objectHostname) { if (actorHostname !== objectHostname) {
return reject('Delete', object, actor); return reject('Delete', object, actor);
} }
const [isNote/* , isActor */] = await Promise.all([ const [isNote, isContext/* , isActor */] = await Promise.all([
posts.exists(pid), posts.exists(id),
activitypub.contexts.getItems(0, id, { returnRootId: true }),
// db.isSortedSetMember('usersRemote:lastCrawled', object.id), // db.isSortedSetMember('usersRemote:lastCrawled', object.id),
]); ]);
switch (true) { switch (true) {
case isNote: { case isNote: {
const cid = await posts.getCidByPid(pid); const cid = await posts.getCidByPid(id);
const allowed = await privileges.categories.can('posts:edit', cid, activitypub._constants.uid); const allowed = await privileges.categories.can('posts:edit', cid, activitypub._constants.uid);
if (!allowed) { if (!allowed) {
return reject('Delete', object, actor); return reject('Delete', object, actor);
} }
const uid = await posts.getPostField(pid, 'uid'); const uid = await posts.getPostField(id, 'uid');
await activitypub.feps.announce(pid, req.body); await activitypub.feps.announce(id, req.body);
await api.posts[method]({ uid }, { pid }); await api.posts[method]({ uid }, { pid: id });
break;
}
case !!isContext: {
const pid = isContext;
const exists = await posts.exists(pid);
if (!exists) {
activitypub.helpers.log(`[activitypub/inbox.delete] Context main pid (${pid}) not found locally. Doing nothing.`);
return;
}
const { tid, uid } = await posts.getPostFields(pid, ['tid', 'uid']);
activitypub.helpers.log(`[activitypub/inbox.delete] Deleting tid ${tid}.`);
await api.topics[method]({ uid }, { tids: [tid] });
break; break;
} }
@@ -238,7 +252,7 @@ inbox.delete = async (req) => {
// } // }
default: { default: {
activitypub.helpers.log(`[activitypub/inbox.delete] Object (${pid}) does not exist locally. Doing nothing.`); activitypub.helpers.log(`[activitypub/inbox.delete] Object (${id}) does not exist locally. Doing nothing.`);
break; break;
} }
} }