perf(server): Reduce database query
This commit is contained in:
		
							parent
							
								
									606e5c0878
								
							
						
					
					
						commit
						e523e54881
					
				
					 2 changed files with 58 additions and 11 deletions
				
			
		|  | @ -1,8 +1,11 @@ | |||
| import { EntityRepository, Repository } from 'typeorm'; | ||||
| import { Users, Notes, UserGroupInvitations, AccessTokens } from '..'; | ||||
| import { EntityRepository, In, Repository } from 'typeorm'; | ||||
| import { Users, Notes, UserGroupInvitations, AccessTokens, NoteReactions } from '..'; | ||||
| import { Notification } from '../entities/notification'; | ||||
| import { awaitAll } from '../../prelude/await-all'; | ||||
| import { SchemaType } from '../../misc/schema'; | ||||
| import { Note } from '../entities/note'; | ||||
| import { NoteReaction } from '../entities/note-reaction'; | ||||
| import { User } from '../entities/user'; | ||||
| 
 | ||||
| export type PackedNotification = SchemaType<typeof packedNotificationSchema>; | ||||
| 
 | ||||
|  | @ -10,6 +13,11 @@ export type PackedNotification = SchemaType<typeof packedNotificationSchema>; | |||
| export class NotificationRepository extends Repository<Notification> { | ||||
| 	public async pack( | ||||
| 		src: Notification['id'] | Notification, | ||||
| 		options: { | ||||
| 			_hintForEachNotes_: { | ||||
| 				myReactions: Map<Note['id'], NoteReaction | null>; | ||||
| 			}; | ||||
| 		} | ||||
| 	): Promise<PackedNotification> { | ||||
| 		const notification = typeof src === 'object' ? src : await this.findOneOrFail(src); | ||||
| 		const token = notification.appAccessTokenId ? await AccessTokens.findOneOrFail(notification.appAccessTokenId) : null; | ||||
|  | @ -22,23 +30,41 @@ export class NotificationRepository extends Repository<Notification> { | |||
| 			userId: notification.notifierId, | ||||
| 			user: notification.notifierId ? Users.pack(notification.notifier || notification.notifierId) : null, | ||||
| 			...(notification.type === 'mention' ? { | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId), | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId, { | ||||
| 					detail: true, | ||||
| 					_hint_: options._hintForEachNotes_ | ||||
| 				}), | ||||
| 			} : {}), | ||||
| 			...(notification.type === 'reply' ? { | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId), | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId, { | ||||
| 					detail: true, | ||||
| 					_hint_: options._hintForEachNotes_ | ||||
| 				}), | ||||
| 			} : {}), | ||||
| 			...(notification.type === 'renote' ? { | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId), | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId, { | ||||
| 					detail: true, | ||||
| 					_hint_: options._hintForEachNotes_ | ||||
| 				}), | ||||
| 			} : {}), | ||||
| 			...(notification.type === 'quote' ? { | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId), | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId, { | ||||
| 					detail: true, | ||||
| 					_hint_: options._hintForEachNotes_ | ||||
| 				}), | ||||
| 			} : {}), | ||||
| 			...(notification.type === 'reaction' ? { | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId), | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId, { | ||||
| 					detail: true, | ||||
| 					_hint_: options._hintForEachNotes_ | ||||
| 				}), | ||||
| 				reaction: notification.reaction | ||||
| 			} : {}), | ||||
| 			...(notification.type === 'pollVote' ? { | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId), | ||||
| 				note: Notes.pack(notification.note || notification.noteId!, notification.notifieeId, { | ||||
| 					detail: true, | ||||
| 					_hint_: options._hintForEachNotes_ | ||||
| 				}), | ||||
| 				choice: notification.choice | ||||
| 			} : {}), | ||||
| 			...(notification.type === 'groupInvited' ? { | ||||
|  | @ -52,10 +78,31 @@ export class NotificationRepository extends Repository<Notification> { | |||
| 		}); | ||||
| 	} | ||||
| 
 | ||||
| 	public packMany( | ||||
| 	public async packMany( | ||||
| 		notifications: Notification[], | ||||
| 		meId: User['id'] | ||||
| 	) { | ||||
| 		return Promise.all(notifications.map(x => this.pack(x))); | ||||
| 		if (notifications.length === 0) return []; | ||||
| 
 | ||||
| 		const notes = notifications.filter(x => x.note != null).map(x => x.note!); | ||||
| 		const noteIds = notes.map(n => n.id); | ||||
| 		const myReactionsMap = new Map<Note['id'], NoteReaction | null>(); | ||||
| 		const renoteIds = notes.filter(n => n.renoteId != null).map(n => n.renoteId!); | ||||
| 		const targets = [...noteIds, ...renoteIds]; | ||||
| 		const myReactions = await NoteReactions.find({ | ||||
| 			userId: meId, | ||||
| 			noteId: In(targets), | ||||
| 		}); | ||||
| 
 | ||||
| 		for (const target of targets) { | ||||
| 			myReactionsMap.set(target, myReactions.find(reaction => reaction.noteId === target) || null); | ||||
| 		} | ||||
| 
 | ||||
| 		return await Promise.all(notifications.map(x => this.pack(x, { | ||||
| 			_hintForEachNotes_: { | ||||
| 				myReactions: myReactionsMap | ||||
| 			} | ||||
| 		}))); | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
|  |  | |||
|  | @ -112,5 +112,5 @@ export default define(meta, async (ps, user) => { | |||
| 		readNotification(user.id, notifications.map(x => x.id)); | ||||
| 	} | ||||
| 
 | ||||
| 	return await Notifications.packMany(notifications); | ||||
| 	return await Notifications.packMany(notifications, user.id); | ||||
| }); | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue