Improve ServiceWorker notification
This commit is contained in:
		@@ -12,7 +12,6 @@ import notify from '../../publishers/notify';
 | 
			
		||||
import NoteWatching from '../../models/note-watching';
 | 
			
		||||
import watch from './watch';
 | 
			
		||||
import Mute from '../../models/mute';
 | 
			
		||||
import pushSw from '../../publishers/push-sw';
 | 
			
		||||
import event from '../../publishers/stream';
 | 
			
		||||
import parse from '../../mfm/parse';
 | 
			
		||||
import { IApp } from '../../models/app';
 | 
			
		||||
@@ -20,56 +19,56 @@ import UserList from '../../models/user-list';
 | 
			
		||||
import resolveUser from '../../remote/resolve-user';
 | 
			
		||||
import Meta from '../../models/meta';
 | 
			
		||||
 | 
			
		||||
type Reason = 'reply' | 'quote' | 'mention';
 | 
			
		||||
type Type = 'reply' | 'renote' | 'quote' | 'mention';
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * ServiceWorkerへの通知を担当
 | 
			
		||||
 * 通知を担当
 | 
			
		||||
 */
 | 
			
		||||
class NotificationManager {
 | 
			
		||||
	private user: IUser;
 | 
			
		||||
	private notifier: IUser;
 | 
			
		||||
	private note: any;
 | 
			
		||||
	private list: Array<{
 | 
			
		||||
		user: ILocalUser['_id'],
 | 
			
		||||
		reason: Reason;
 | 
			
		||||
	private queue: Array<{
 | 
			
		||||
		notifiee: ILocalUser['_id'],
 | 
			
		||||
		type: Type;
 | 
			
		||||
	}> = [];
 | 
			
		||||
 | 
			
		||||
	constructor(user: IUser, note: any) {
 | 
			
		||||
		this.user = user;
 | 
			
		||||
	constructor(notifier: IUser, note: any) {
 | 
			
		||||
		this.notifier = notifier;
 | 
			
		||||
		this.note = note;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	public push(user: ILocalUser['_id'], reason: Reason) {
 | 
			
		||||
	public push(notifiee: ILocalUser['_id'], type: Type) {
 | 
			
		||||
		// 自分自身へは通知しない
 | 
			
		||||
		if (this.user._id.equals(user)) return;
 | 
			
		||||
		if (this.notifier._id.equals(notifiee)) return;
 | 
			
		||||
 | 
			
		||||
		const exist = this.list.find(x => x.user.equals(user));
 | 
			
		||||
		const exist = this.queue.find(x => x.notifiee.equals(notifiee));
 | 
			
		||||
 | 
			
		||||
		if (exist) {
 | 
			
		||||
			// 「メンションされているかつ返信されている」場合は、メンションとしての通知ではなく返信としての通知にする
 | 
			
		||||
			if (reason != 'mention') {
 | 
			
		||||
				exist.reason = reason;
 | 
			
		||||
			if (type != 'mention') {
 | 
			
		||||
				exist.type = type;
 | 
			
		||||
			}
 | 
			
		||||
		} else {
 | 
			
		||||
			this.list.push({
 | 
			
		||||
				user, reason
 | 
			
		||||
			this.queue.push({
 | 
			
		||||
				notifiee, type
 | 
			
		||||
			});
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	public deliver() {
 | 
			
		||||
		this.list.forEach(async x => {
 | 
			
		||||
			const mentionee = x.user;
 | 
			
		||||
 | 
			
		||||
		this.queue.forEach(async x => {
 | 
			
		||||
			// ミュート情報を取得
 | 
			
		||||
			const mentioneeMutes = await Mute.find({
 | 
			
		||||
				muterId: mentionee
 | 
			
		||||
				muterId: x.notifiee
 | 
			
		||||
			});
 | 
			
		||||
 | 
			
		||||
			const mentioneesMutedUserIds = mentioneeMutes.map(m => m.muteeId.toString());
 | 
			
		||||
 | 
			
		||||
			// 通知される側のユーザーが通知する側のユーザーをミュートしていない限りは通知する
 | 
			
		||||
			if (!mentioneesMutedUserIds.includes(this.user._id.toString())) {
 | 
			
		||||
				pushSw(mentionee, x.reason, this.note);
 | 
			
		||||
			if (!mentioneesMutedUserIds.includes(this.notifier._id.toString())) {
 | 
			
		||||
				notify(x.notifiee, this.notifier._id, x.type, {
 | 
			
		||||
					noteId: this.note._id
 | 
			
		||||
				});
 | 
			
		||||
			}
 | 
			
		||||
		});
 | 
			
		||||
	}
 | 
			
		||||
@@ -264,10 +263,6 @@ export default async (user: IUser, data: {
 | 
			
		||||
			if (data.renote && data.renote.userId.equals(u._id)) return;
 | 
			
		||||
 | 
			
		||||
			// Create notification
 | 
			
		||||
			notify(u._id, user._id, 'mention', {
 | 
			
		||||
				noteId: note._id
 | 
			
		||||
			});
 | 
			
		||||
 | 
			
		||||
			nm.push(u._id, 'mention');
 | 
			
		||||
		});
 | 
			
		||||
 | 
			
		||||
@@ -371,11 +366,6 @@ export default async (user: IUser, data: {
 | 
			
		||||
			}
 | 
			
		||||
		});
 | 
			
		||||
 | 
			
		||||
		// (自分自身へのリプライでない限りは)通知を作成
 | 
			
		||||
		notify(data.reply.userId, user._id, 'reply', {
 | 
			
		||||
			noteId: note._id
 | 
			
		||||
		});
 | 
			
		||||
 | 
			
		||||
		// Fetch watchers
 | 
			
		||||
		NoteWatching.find({
 | 
			
		||||
			noteId: data.reply._id,
 | 
			
		||||
@@ -388,9 +378,7 @@ export default async (user: IUser, data: {
 | 
			
		||||
			}
 | 
			
		||||
		}).then(watchers => {
 | 
			
		||||
			watchers.forEach(watcher => {
 | 
			
		||||
				notify(watcher.userId, user._id, 'reply', {
 | 
			
		||||
					noteId: note._id
 | 
			
		||||
				});
 | 
			
		||||
				nm.push(watcher.userId, 'reply');
 | 
			
		||||
			});
 | 
			
		||||
		});
 | 
			
		||||
 | 
			
		||||
@@ -399,6 +387,7 @@ export default async (user: IUser, data: {
 | 
			
		||||
			watch(user._id, data.reply);
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		// (自分自身へのリプライでない限りは)通知を作成
 | 
			
		||||
		nm.push(data.reply.userId, 'reply');
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
@@ -406,9 +395,7 @@ export default async (user: IUser, data: {
 | 
			
		||||
	if (data.renote) {
 | 
			
		||||
		// Notify
 | 
			
		||||
		const type = data.text ? 'quote' : 'renote';
 | 
			
		||||
		notify(data.renote.userId, user._id, type, {
 | 
			
		||||
			noteId: note._id
 | 
			
		||||
		});
 | 
			
		||||
		nm.push(data.renote.userId, type);
 | 
			
		||||
 | 
			
		||||
		// Fetch watchers
 | 
			
		||||
		NoteWatching.find({
 | 
			
		||||
@@ -420,9 +407,7 @@ export default async (user: IUser, data: {
 | 
			
		||||
			}
 | 
			
		||||
		}).then(watchers => {
 | 
			
		||||
			watchers.forEach(watcher => {
 | 
			
		||||
				notify(watcher.userId, user._id, type, {
 | 
			
		||||
					noteId: note._id
 | 
			
		||||
				});
 | 
			
		||||
				nm.push(watcher.userId, type);
 | 
			
		||||
			});
 | 
			
		||||
		});
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -1,9 +1,8 @@
 | 
			
		||||
import { IUser, pack as packUser, isLocalUser, isRemoteUser } from '../../../models/user';
 | 
			
		||||
import Note, { INote, pack as packNote } from '../../../models/note';
 | 
			
		||||
import { IUser, isLocalUser, isRemoteUser } from '../../../models/user';
 | 
			
		||||
import Note, { INote } from '../../../models/note';
 | 
			
		||||
import NoteReaction from '../../../models/note-reaction';
 | 
			
		||||
import { publishNoteStream } from '../../../publishers/stream';
 | 
			
		||||
import notify from '../../../publishers/notify';
 | 
			
		||||
import pushSw from '../../../publishers/push-sw';
 | 
			
		||||
import NoteWatching from '../../../models/note-watching';
 | 
			
		||||
import watch from '../watch';
 | 
			
		||||
import renderLike from '../../../remote/activitypub/renderer/like';
 | 
			
		||||
@@ -54,12 +53,6 @@ export default async (user: IUser, note: INote, reaction: string) => new Promise
 | 
			
		||||
		});
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	pushSw(note.userId, 'reaction', {
 | 
			
		||||
		user: await packUser(user, note.userId),
 | 
			
		||||
		note: await packNote(note, note.userId),
 | 
			
		||||
		reaction: reaction
 | 
			
		||||
	});
 | 
			
		||||
 | 
			
		||||
	// Fetch watchers
 | 
			
		||||
	NoteWatching
 | 
			
		||||
		.find({
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user