Sifa professional network API (Fastify, AT Protocol, Jetstream) sifa.id/

fix(follow): deduplicate following list by subjectDid (#138)

Users followed on both Sifa and Bluesky appeared twice in the
/api/following response. Deduplicate by subjectDid, preferring the
sifa source row so the Unfollow button is available.

Fixes singi-labs/sifa-web#317

authored by

Guido X Jansen and committed by
GitHub
db4a4914 fa94cafe

+16 -2
+16 -2
src/routes/follow.ts
··· 156 156 .orderBy(sql`${connections.createdAt} DESC`) 157 157 .limit(limit + 1); 158 158 159 - const hasMore = rows.length > limit; 160 - const items = hasMore ? rows.slice(0, limit) : rows; 159 + // Deduplicate by subjectDid, preferring 'sifa' source over others. 160 + // A user followed on both Sifa and Bluesky should appear once with source=sifa. 161 + const deduped: typeof rows = []; 162 + const seen = new Map<string, number>(); 163 + for (const row of rows) { 164 + const idx = seen.get(row.subjectDid); 165 + if (idx === undefined) { 166 + seen.set(row.subjectDid, deduped.length); 167 + deduped.push(row); 168 + } else if (row.source === 'sifa' && deduped[idx]?.source !== 'sifa') { 169 + deduped[idx] = row; 170 + } 171 + } 172 + 173 + const hasMore = deduped.length > limit; 174 + const items = hasMore ? deduped.slice(0, limit) : deduped; 161 175 162 176 // Enrich rows without profile data from Bluesky 163 177 const needEnrich = items.filter((r) => !r.handle).map((r) => r.subjectDid);