From 06ac3142a8d5779e6ed931bbbb27a00e09b24ce3 Mon Sep 17 00:00:00 2001 From: Julien Calixte Date: Tue, 10 Mar 2026 15:51:10 +0100 Subject: [PATCH] feat: add POST /notes/feed endpoint for multi-DID filtering --- server.ts | 12 ++++++++++++ src/data/db.ts | 17 +++++++++++++++++ 2 files changed, 29 insertions(+) diff --git a/server.ts b/server.ts index 8584c93..6afeb4f 100644 --- a/server.ts +++ b/server.ts @@ -4,6 +4,7 @@ import { deleteWebhooksByDid, getNotes, getNotesByDid, + getNotesByDids, } from "./src/data/db.ts"; import { log } from "./src/log.ts"; @@ -28,6 +29,17 @@ router.get("/:did/notes", (ctx) => { ctx.response.body = getNotesByDid(did, cursor, limit); }); +router.post("/notes/feed", async (ctx) => { + const body = await ctx.request.body.json(); + const { dids, cursor, limit } = body ?? {}; + if (!Array.isArray(dids) || dids.length === 0) { + ctx.response.status = 400; + ctx.response.body = { error: "dids must be a non-empty array" }; + return; + } + ctx.response.body = getNotesByDids(dids, cursor, Number(limit) || PAGINATION); +}); + router.post("/:did/webhooks", async (ctx) => { const { did } = ctx.params; const body = await ctx.request.body.json(); diff --git a/src/data/db.ts b/src/data/db.ts index fc989da..f60c804 100644 --- a/src/data/db.ts +++ b/src/data/db.ts @@ -49,6 +49,23 @@ export const getNotesByDid = (did: string, cursor?: string, limit = 20) => { }; }; +export const getNotesByDids = (dids: string[], cursor?: string, limit = 20) => { + if (dids.length === 0) return { notes: [] }; + const placeholders = dids.map(() => "?").join(", "); + const notes = cursor + ? db.prepare( + `SELECT did, rkey, title, publishedAt, createdAt, language FROM note WHERE discoverable = 1 AND did IN (${placeholders}) AND rkey < ? ORDER BY rkey DESC LIMIT ?`, + ).all(...dids, cursor, limit) + : db.prepare( + `SELECT did, rkey, title, publishedAt, createdAt, language FROM note WHERE discoverable = 1 AND did IN (${placeholders}) ORDER BY rkey DESC LIMIT ?`, + ).all(...dids, limit); + + return { + notes, + cursor: notes.length === limit ? notes[notes.length - 1].rkey : undefined, + }; +}; + export const deleteNote = ({ did, rkey }: { did: string; rkey: string }) => { db.exec("DELETE FROM note WHERE did = ? AND rkey = ?", did, rkey); };