diff options
| author | syuilo <Syuilotan@yahoo.co.jp> | 2023-10-11 10:15:44 +0900 |
|---|---|---|
| committer | syuilo <Syuilotan@yahoo.co.jp> | 2023-10-11 10:15:44 +0900 |
| commit | 7a8d5e58400a51218d673211219111238a8b7ae8 (patch) | |
| tree | 3d1a3708337098d735a2ace446de44b46f0204bf /packages/backend/src/server | |
| parent | fix(backend): フォローしているユーザーからの自分の投稿... (diff) | |
| download | sharkey-7a8d5e58400a51218d673211219111238a8b7ae8.tar.gz sharkey-7a8d5e58400a51218d673211219111238a8b7ae8.tar.bz2 sharkey-7a8d5e58400a51218d673211219111238a8b7ae8.zip | |
enhance: ローカルタイムライン、ソーシャルタイムラインで返信を含むかどうか設定可能に
Resolve #12001
Diffstat (limited to 'packages/backend/src/server')
4 files changed, 45 insertions, 8 deletions
diff --git a/packages/backend/src/server/api/endpoints/notes/hybrid-timeline.ts b/packages/backend/src/server/api/endpoints/notes/hybrid-timeline.ts index 1b77285d47..8ac5f1b038 100644 --- a/packages/backend/src/server/api/endpoints/notes/hybrid-timeline.ts +++ b/packages/backend/src/server/api/endpoints/notes/hybrid-timeline.ts @@ -55,6 +55,7 @@ export const paramDef = { includeLocalRenotes: { type: 'boolean', default: true }, withFiles: { type: 'boolean', default: false }, withRenotes: { type: 'boolean', default: true }, + withReplies: { type: 'boolean', default: false }, }, required: [], } as const; @@ -94,12 +95,29 @@ export default class extends Endpoint<typeof meta, typeof paramDef> { // eslint- this.cacheService.userBlockedCache.fetch(me.id), ]); - const [htlNoteIds, ltlNoteIds] = await this.redisTimelineService.getMulti([ - ps.withFiles ? `homeTimelineWithFiles:${me.id}` : `homeTimeline:${me.id}`, - ps.withFiles ? 'localTimelineWithFiles' : 'localTimeline', - ], untilId, sinceId); + let noteIds: string[]; + + if (ps.withFiles) { + const [htlNoteIds, ltlNoteIds] = await this.redisTimelineService.getMulti([ + `homeTimelineWithFiles:${me.id}`, + 'localTimelineWithFiles', + ], untilId, sinceId); + noteIds = Array.from(new Set([...htlNoteIds, ...ltlNoteIds])); + } else if (ps.withReplies) { + const [htlNoteIds, ltlNoteIds, ltlReplyNoteIds] = await this.redisTimelineService.getMulti([ + `homeTimeline:${me.id}`, + 'localTimeline', + 'localTimelineWithReplies', + ], untilId, sinceId); + noteIds = Array.from(new Set([...htlNoteIds, ...ltlNoteIds, ...ltlReplyNoteIds])); + } else { + const [htlNoteIds, ltlNoteIds] = await this.redisTimelineService.getMulti([ + `homeTimeline:${me.id}`, + 'localTimeline', + ], untilId, sinceId); + noteIds = Array.from(new Set([...htlNoteIds, ...ltlNoteIds])); + } - let noteIds = Array.from(new Set([...htlNoteIds, ...ltlNoteIds])); noteIds.sort((a, b) => a > b ? -1 : 1); noteIds = noteIds.slice(0, ps.limit); diff --git a/packages/backend/src/server/api/endpoints/notes/local-timeline.ts b/packages/backend/src/server/api/endpoints/notes/local-timeline.ts index 2357f32d5e..55b5d47386 100644 --- a/packages/backend/src/server/api/endpoints/notes/local-timeline.ts +++ b/packages/backend/src/server/api/endpoints/notes/local-timeline.ts @@ -45,6 +45,7 @@ export const paramDef = { properties: { withFiles: { type: 'boolean', default: false }, withRenotes: { type: 'boolean', default: true }, + withReplies: { type: 'boolean', default: false }, excludeNsfw: { type: 'boolean', default: false }, limit: { type: 'integer', minimum: 1, maximum: 100, default: 10 }, sinceId: { type: 'string', format: 'misskey:id' }, @@ -90,7 +91,21 @@ export default class extends Endpoint<typeof meta, typeof paramDef> { // eslint- this.cacheService.userBlockedCache.fetch(me.id), ]) : [new Set<string>(), new Set<string>(), new Set<string>()]; - let noteIds = await this.redisTimelineService.get(ps.withFiles ? 'localTimelineWithFiles' : 'localTimeline', untilId, sinceId); + let noteIds: string[]; + + if (ps.withFiles) { + noteIds = await this.redisTimelineService.get('localTimelineWithFiles', untilId, sinceId); + } else if (ps.withReplies) { + const [nonReplyNoteIds, replyNoteIds] = await this.redisTimelineService.getMulti([ + 'localTimeline', + 'localTimelineWithReplies', + ], untilId, sinceId); + noteIds = Array.from(new Set([...nonReplyNoteIds, ...replyNoteIds])); + noteIds.sort((a, b) => a > b ? -1 : 1); + } else { + noteIds = await this.redisTimelineService.get('localTimeline', untilId, sinceId); + } + noteIds = noteIds.slice(0, ps.limit); if (noteIds.length === 0) { diff --git a/packages/backend/src/server/api/stream/channels/hybrid-timeline.ts b/packages/backend/src/server/api/stream/channels/hybrid-timeline.ts index d5f5d54e46..adedca5152 100644 --- a/packages/backend/src/server/api/stream/channels/hybrid-timeline.ts +++ b/packages/backend/src/server/api/stream/channels/hybrid-timeline.ts @@ -19,6 +19,7 @@ class HybridTimelineChannel extends Channel { public static shouldShare = false; public static requireCredential = true; private withRenotes: boolean; + private withReplies: boolean; private withFiles: boolean; constructor( @@ -39,6 +40,7 @@ class HybridTimelineChannel extends Channel { if (!policies.ltlAvailable) return; this.withRenotes = params.withRenotes ?? true; + this.withReplies = params.withReplies ?? false; this.withFiles = params.withFiles ?? false; // Subscribe events @@ -87,7 +89,7 @@ class HybridTimelineChannel extends Channel { if (isInstanceMuted(note, new Set<string>(this.userProfile!.mutedInstances ?? []))) return; // 関係ない返信は除外 - if (note.reply && !this.following[note.userId]?.withReplies) { + if (note.reply && !this.following[note.userId]?.withReplies && !this.withReplies) { const reply = note.reply; // 「チャンネル接続主への返信」でもなければ、「チャンネル接続主が行った返信」でもなければ、「投稿者の投稿者自身への返信」でもない場合 if (reply.userId !== this.user!.id && note.userId !== this.user!.id && reply.userId !== note.userId) return; diff --git a/packages/backend/src/server/api/stream/channels/local-timeline.ts b/packages/backend/src/server/api/stream/channels/local-timeline.ts index 94c22f8915..69aa366f00 100644 --- a/packages/backend/src/server/api/stream/channels/local-timeline.ts +++ b/packages/backend/src/server/api/stream/channels/local-timeline.ts @@ -18,6 +18,7 @@ class LocalTimelineChannel extends Channel { public static shouldShare = false; public static requireCredential = false; private withRenotes: boolean; + private withReplies: boolean; private withFiles: boolean; constructor( @@ -38,6 +39,7 @@ class LocalTimelineChannel extends Channel { if (!policies.ltlAvailable) return; this.withRenotes = params.withRenotes ?? true; + this.withReplies = params.withReplies ?? false; this.withFiles = params.withFiles ?? false; // Subscribe events @@ -66,7 +68,7 @@ class LocalTimelineChannel extends Channel { } // 関係ない返信は除外 - if (note.reply && this.user && !this.following[note.userId]?.withReplies) { + if (note.reply && this.user && !this.following[note.userId]?.withReplies && !this.withReplies) { const reply = note.reply; // 「チャンネル接続主への返信」でもなければ、「チャンネル接続主が行った返信」でもなければ、「投稿者の投稿者自身への返信」でもない場合 if (reply.userId !== this.user.id && note.userId !== this.user.id && reply.userId !== note.userId) return; |