fix(backend): fix liked collection

The `liked` collection is a list of objects liked by the actor, not the
associated `Like` activities.
This commit is contained in:
Daiki Mizukami 2024-08-14 13:00:32 +09:00
parent d88193a16e
commit 985d582166
No known key found for this signature in database
GPG key ID: 10478E598B944AA2

View file

@ -13,7 +13,7 @@ import accepts from 'accepts';
import vary from 'vary'; import vary from 'vary';
import secureJson from 'secure-json-parse'; import secureJson from 'secure-json-parse';
import { DI } from '@/di-symbols.js'; import { DI } from '@/di-symbols.js';
import type { FollowingsRepository, NotesRepository, EmojisRepository, NoteReactionsRepository, UserProfilesRepository, UserNotePiningsRepository, UsersRepository, FollowRequestsRepository, MiNoteReaction } from '@/models/_.js'; import type { FollowingsRepository, NotesRepository, EmojisRepository, NoteReactionsRepository, UserProfilesRepository, UserNotePiningsRepository, UsersRepository, FollowRequestsRepository } from '@/models/_.js';
import * as url from '@/misc/prelude/url.js'; import * as url from '@/misc/prelude/url.js';
import type { Config } from '@/config.js'; import type { Config } from '@/config.js';
import { ApRendererService } from '@/core/activitypub/ApRendererService.js'; import { ApRendererService } from '@/core/activitypub/ApRendererService.js';
@ -386,36 +386,37 @@ export class ActivityPubServerService {
const limit = 10; const limit = 10;
const partOf = `${this.config.url}/users/${userId}/liked`; const partOf = `${this.config.url}/users/${userId}/liked`;
const query = { const query = this.noteReactionsRepository.createQueryBuilder('reaction')
userId: user.id, .andWhere('reaction.userId = :userId', { userId: user.id });
} as FindOptionsWhere<MiNoteReaction>;
if (page) { if (page) {
const countPromise = query.getCount();
// カーソルが指定されている場合 // カーソルが指定されている場合
if (cursor) { if (cursor) {
query.id = LessThan(cursor); query.andWhere('reaction.id < :id', { id: cursor });
} }
const [reactions, reactionsCount] = await Promise.all([ const [reactions, reactionsCount] = await Promise.all([
this.noteReactionsRepository.find({ query
where: query, .limit(limit + 1)
take: limit + 1, .orderBy('reaction.id', 'DESC')
order: { id: -1 }, .innerJoinAndSelect('reaction.note', 'note')
}), .getMany(),
this.noteReactionsRepository.count({ where: query }), countPromise,
]); ]);
// 「次のページ」があるかどうか // 「次のページ」があるかどうか
const inStock = reactions.length === limit + 1; const inStock = reactions.length === limit + 1;
if (inStock) reactions.pop(); if (inStock) reactions.pop();
const renderedLikes = await Promise.all(reactions.map(reaction => this.apRendererService.renderLike(reaction, { uri: null }))); const reactedNoteUris = await Promise.all(reactions.map(reaction => reaction.note!.uri || `${this.config.url}/notes/${reaction.note!.uri}`));
const rendered = this.apRendererService.renderOrderedCollectionPage( const rendered = this.apRendererService.renderOrderedCollectionPage(
`${partOf}?${url.query({ `${partOf}?${url.query({
page: 'true', page: 'true',
cursor, cursor,
})}`, })}`,
reactionsCount, renderedLikes, partOf, reactionsCount, reactedNoteUris, partOf,
undefined, undefined,
inStock ? `${partOf}?${url.query({ inStock ? `${partOf}?${url.query({
page: 'true', page: 'true',
@ -427,7 +428,7 @@ export class ActivityPubServerService {
return (this.apRendererService.addContext(rendered)); return (this.apRendererService.addContext(rendered));
} else { } else {
// index page // index page
const reactionsCount = await this.noteReactionsRepository.count({ where: query }); const reactionsCount = await query.getCount();
const rendered = this.apRendererService.renderOrderedCollection( const rendered = this.apRendererService.renderOrderedCollection(
partOf, partOf,
reactionsCount, reactionsCount,