parent
10be4267b1
commit
796492e3bf
@ -1,4 +1,5 @@
|
|||||||
# DIFFRENCE
|
# DIFFRENCE
|
||||||
|
<<<<<<< HEAD
|
||||||
## 2024.9.0-yami-1.3.1
|
## 2024.9.0-yami-1.3.1
|
||||||
## Client
|
## Client
|
||||||
- フォロー/フォロワー/アナウンス/みつける/Play/ギャラリー/チャンネル/TL/ユーザー/ノートのページをログイン必須に
|
- フォロー/フォロワー/アナウンス/みつける/Play/ギャラリー/チャンネル/TL/ユーザー/ノートのページをログイン必須に
|
||||||
@ -28,6 +29,8 @@
|
|||||||
### Server
|
### Server
|
||||||
- `notes/show`, `users/notes`の認証を不要に(revert?)
|
- `notes/show`, `users/notes`の認証を不要に(revert?)
|
||||||
|
|
||||||
|
=======
|
||||||
|
>>>>>>> 12828a4aa2 (Merge pull request #35 from lqvp/master)
|
||||||
## 2024.9.0-yami-1.2.5
|
## 2024.9.0-yami-1.2.5
|
||||||
### Feat
|
### Feat
|
||||||
- フォロー解除時にも通知するように
|
- フォロー解除時にも通知するように
|
||||||
|
@ -68,6 +68,7 @@ loadMore: "Load more"
|
|||||||
showMore: "Show more"
|
showMore: "Show more"
|
||||||
showLess: "Close"
|
showLess: "Close"
|
||||||
youGotNewFollower: "followed you"
|
youGotNewFollower: "followed you"
|
||||||
|
youGotUnFollower: "unfollowed you"
|
||||||
receiveFollowRequest: "Follow request received"
|
receiveFollowRequest: "Follow request received"
|
||||||
followRequestAccepted: "Follow request accepted"
|
followRequestAccepted: "Follow request accepted"
|
||||||
mention: "Mention"
|
mention: "Mention"
|
||||||
@ -1884,6 +1885,8 @@ _gallery:
|
|||||||
_email:
|
_email:
|
||||||
_follow:
|
_follow:
|
||||||
title: "You've got a new follower"
|
title: "You've got a new follower"
|
||||||
|
_unfollow:
|
||||||
|
title: "You have been unfollowed"
|
||||||
_receiveFollowRequest:
|
_receiveFollowRequest:
|
||||||
title: "You've received a follow request"
|
title: "You've received a follow request"
|
||||||
_plugin:
|
_plugin:
|
||||||
@ -2440,6 +2443,7 @@ _notification:
|
|||||||
youGotQuote: "{name} quoted you"
|
youGotQuote: "{name} quoted you"
|
||||||
youRenoted: "Boost from {name}"
|
youRenoted: "Boost from {name}"
|
||||||
youWereFollowed: "followed you"
|
youWereFollowed: "followed you"
|
||||||
|
youWereUnFollower: "unfollowed you"
|
||||||
youReceivedFollowRequest: "You've received a follow request"
|
youReceivedFollowRequest: "You've received a follow request"
|
||||||
yourFollowRequestAccepted: "Your follow request was accepted"
|
yourFollowRequestAccepted: "Your follow request was accepted"
|
||||||
pollEnded: "Poll results have become available"
|
pollEnded: "Poll results have become available"
|
||||||
@ -2456,12 +2460,14 @@ _notification:
|
|||||||
likedBySomeUsers: "{n} users liked your note"
|
likedBySomeUsers: "{n} users liked your note"
|
||||||
renotedBySomeUsers: "Boosted by {n} users"
|
renotedBySomeUsers: "Boosted by {n} users"
|
||||||
followedBySomeUsers: "Followed by {n} users"
|
followedBySomeUsers: "Followed by {n} users"
|
||||||
|
unfollowerBySomeUsers: "UnFollowed by {n} users"
|
||||||
flushNotification: "Clear notifications"
|
flushNotification: "Clear notifications"
|
||||||
edited: "Note got edited"
|
edited: "Note got edited"
|
||||||
_types:
|
_types:
|
||||||
all: "All"
|
all: "All"
|
||||||
note: "New notes"
|
note: "New notes"
|
||||||
follow: "New followers"
|
follow: "New followers"
|
||||||
|
unfollow: "Unfollowers"
|
||||||
mention: "Mentions"
|
mention: "Mentions"
|
||||||
reply: "Replies"
|
reply: "Replies"
|
||||||
renote: "Boosts"
|
renote: "Boosts"
|
||||||
|
22
locales/index.d.ts
vendored
22
locales/index.d.ts
vendored
@ -288,6 +288,10 @@ export interface Locale extends ILocale {
|
|||||||
* フォローされました
|
* フォローされました
|
||||||
*/
|
*/
|
||||||
"youGotNewFollower": string;
|
"youGotNewFollower": string;
|
||||||
|
/**
|
||||||
|
* フォロー解除されました
|
||||||
|
*/
|
||||||
|
"youGotUnFollower": string;
|
||||||
/**
|
/**
|
||||||
* フォローリクエストされました
|
* フォローリクエストされました
|
||||||
*/
|
*/
|
||||||
@ -7340,6 +7344,12 @@ export interface Locale extends ILocale {
|
|||||||
*/
|
*/
|
||||||
"title": string;
|
"title": string;
|
||||||
};
|
};
|
||||||
|
"_unfollow" : {
|
||||||
|
/**
|
||||||
|
* フォロー解除されました
|
||||||
|
*/
|
||||||
|
"title": string;
|
||||||
|
}
|
||||||
"_receiveFollowRequest": {
|
"_receiveFollowRequest": {
|
||||||
/**
|
/**
|
||||||
* フォローリクエストを受け取りました
|
* フォローリクエストを受け取りました
|
||||||
@ -9480,6 +9490,10 @@ export interface Locale extends ILocale {
|
|||||||
* フォローされました
|
* フォローされました
|
||||||
*/
|
*/
|
||||||
"youWereFollowed": string;
|
"youWereFollowed": string;
|
||||||
|
/**
|
||||||
|
* フォロー解除されました
|
||||||
|
*/
|
||||||
|
"youWereUnFollower": string;
|
||||||
/**
|
/**
|
||||||
* フォローリクエストが来ました
|
* フォローリクエストが来ました
|
||||||
*/
|
*/
|
||||||
@ -9548,6 +9562,10 @@ export interface Locale extends ILocale {
|
|||||||
* {n}人にフォローされました
|
* {n}人にフォローされました
|
||||||
*/
|
*/
|
||||||
"followedBySomeUsers": ParameterizedString<"n">;
|
"followedBySomeUsers": ParameterizedString<"n">;
|
||||||
|
/**
|
||||||
|
* {n}人にフォロー解除されました
|
||||||
|
*/
|
||||||
|
"unfollowerBySomeUser": ParameterizedString<"n">;
|
||||||
/**
|
/**
|
||||||
* 通知の履歴をリセットする
|
* 通知の履歴をリセットする
|
||||||
*/
|
*/
|
||||||
@ -9565,6 +9583,10 @@ export interface Locale extends ILocale {
|
|||||||
* フォロー
|
* フォロー
|
||||||
*/
|
*/
|
||||||
"follow": string;
|
"follow": string;
|
||||||
|
/**
|
||||||
|
* フォロー解除
|
||||||
|
*/
|
||||||
|
"unfollow": string;
|
||||||
/**
|
/**
|
||||||
* メンション
|
* メンション
|
||||||
*/
|
*/
|
||||||
|
@ -68,6 +68,7 @@ loadMore: "もっと見る"
|
|||||||
showMore: "もっと見る"
|
showMore: "もっと見る"
|
||||||
showLess: "閉じる"
|
showLess: "閉じる"
|
||||||
youGotNewFollower: "フォローされました"
|
youGotNewFollower: "フォローされました"
|
||||||
|
youGotUnFollower: "フォロー解除されました"
|
||||||
receiveFollowRequest: "フォローリクエストされました"
|
receiveFollowRequest: "フォローリクエストされました"
|
||||||
followRequestAccepted: "フォローが承認されました"
|
followRequestAccepted: "フォローが承認されました"
|
||||||
mention: "メンション"
|
mention: "メンション"
|
||||||
@ -1907,6 +1908,8 @@ _gallery:
|
|||||||
_email:
|
_email:
|
||||||
_follow:
|
_follow:
|
||||||
title: "フォローされました"
|
title: "フォローされました"
|
||||||
|
_unfollow:
|
||||||
|
title: "フォロー解除されました"
|
||||||
_receiveFollowRequest:
|
_receiveFollowRequest:
|
||||||
title: "フォローリクエストを受け取りました"
|
title: "フォローリクエストを受け取りました"
|
||||||
|
|
||||||
@ -2501,6 +2504,7 @@ _notification:
|
|||||||
youGotQuote: "{name}による引用"
|
youGotQuote: "{name}による引用"
|
||||||
youRenoted: "{name}がBoostしました"
|
youRenoted: "{name}がBoostしました"
|
||||||
youWereFollowed: "フォローされました"
|
youWereFollowed: "フォローされました"
|
||||||
|
youWereUnFollower: "フォロー解除されました"
|
||||||
youReceivedFollowRequest: "フォローリクエストが来ました"
|
youReceivedFollowRequest: "フォローリクエストが来ました"
|
||||||
yourFollowRequestAccepted: "フォローリクエストが承認されました"
|
yourFollowRequestAccepted: "フォローリクエストが承認されました"
|
||||||
pollEnded: "アンケートの結果が出ました"
|
pollEnded: "アンケートの結果が出ました"
|
||||||
@ -2518,12 +2522,14 @@ _notification:
|
|||||||
likedBySomeUsers: "{n}人がいいねしました"
|
likedBySomeUsers: "{n}人がいいねしました"
|
||||||
renotedBySomeUsers: "{n}人がリノートしました"
|
renotedBySomeUsers: "{n}人がリノートしました"
|
||||||
followedBySomeUsers: "{n}人にフォローされました"
|
followedBySomeUsers: "{n}人にフォローされました"
|
||||||
|
unfollowerBySomeUsers: "{n}人にフォロー解除されました"
|
||||||
flushNotification: "通知の履歴をリセットする"
|
flushNotification: "通知の履歴をリセットする"
|
||||||
|
|
||||||
_types:
|
_types:
|
||||||
all: "すべて"
|
all: "すべて"
|
||||||
note: "ユーザーの新規投稿"
|
note: "ユーザーの新規投稿"
|
||||||
follow: "フォロー"
|
follow: "フォロー"
|
||||||
|
unfollow: "フォロー解除"
|
||||||
mention: "メンション"
|
mention: "メンション"
|
||||||
reply: "リプライ"
|
reply: "リプライ"
|
||||||
renote: "Boost"
|
renote: "Boost"
|
||||||
|
@ -66,6 +66,7 @@ loadMore: "まだまだあるで!"
|
|||||||
showMore: "まだまだあるで!"
|
showMore: "まだまだあるで!"
|
||||||
showLess: "さいなら"
|
showLess: "さいなら"
|
||||||
youGotNewFollower: "フォローされたで"
|
youGotNewFollower: "フォローされたで"
|
||||||
|
youGotUnFollower: "フォロー解除されたで"
|
||||||
receiveFollowRequest: "フォローリクエストされたで"
|
receiveFollowRequest: "フォローリクエストされたで"
|
||||||
followRequestAccepted: "フォローが承認されたで"
|
followRequestAccepted: "フォローが承認されたで"
|
||||||
mention: "メンション"
|
mention: "メンション"
|
||||||
@ -1806,6 +1807,8 @@ _gallery:
|
|||||||
_email:
|
_email:
|
||||||
_follow:
|
_follow:
|
||||||
title: "フォローされたで"
|
title: "フォローされたで"
|
||||||
|
_unfollow:
|
||||||
|
title: "フォロー解除されたで"
|
||||||
_receiveFollowRequest:
|
_receiveFollowRequest:
|
||||||
title: "フォローリクエストを受け取ったで"
|
title: "フォローリクエストを受け取ったで"
|
||||||
_plugin:
|
_plugin:
|
||||||
@ -2349,6 +2352,7 @@ _notification:
|
|||||||
youGotQuote: "{name}による引用"
|
youGotQuote: "{name}による引用"
|
||||||
youRenoted: "{name}がブーストしたみたいやで"
|
youRenoted: "{name}がブーストしたみたいやで"
|
||||||
youWereFollowed: "フォローされたで"
|
youWereFollowed: "フォローされたで"
|
||||||
|
youWereUnFollower: "フォロー解除されたで"
|
||||||
youReceivedFollowRequest: "フォロー許可してほしいみたいやな"
|
youReceivedFollowRequest: "フォロー許可してほしいみたいやな"
|
||||||
yourFollowRequestAccepted: "フォローさせてもろたで"
|
yourFollowRequestAccepted: "フォローさせてもろたで"
|
||||||
pollEnded: "アンケートの結果が出たみたいや"
|
pollEnded: "アンケートの結果が出たみたいや"
|
||||||
@ -2365,11 +2369,13 @@ _notification:
|
|||||||
likedBySomeUsers: "{n}人がいいねしたで"
|
likedBySomeUsers: "{n}人がいいねしたで"
|
||||||
renotedBySomeUsers: "{n}人がブーストしたで"
|
renotedBySomeUsers: "{n}人がブーストしたで"
|
||||||
followedBySomeUsers: "{n}人にフォローされたで"
|
followedBySomeUsers: "{n}人にフォローされたで"
|
||||||
|
unfollowerBySomeUser: "{n}人にフォロー解除されたで"
|
||||||
flushNotification: "通知の履歴をリセットする"
|
flushNotification: "通知の履歴をリセットする"
|
||||||
_types:
|
_types:
|
||||||
all: "すべて"
|
all: "すべて"
|
||||||
note: "あんたらの新規投稿"
|
note: "あんたらの新規投稿"
|
||||||
follow: "フォロー"
|
follow: "フォロー"
|
||||||
|
unfollow: "フォロー解除"
|
||||||
mention: "メンション"
|
mention: "メンション"
|
||||||
reply: "リプライ"
|
reply: "リプライ"
|
||||||
renote: "Renote"
|
renote: "Renote"
|
||||||
|
BIN
packages/backend/assets/tabler-badges/user-minus.png
Normal file
BIN
packages/backend/assets/tabler-badges/user-minus.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 471 B |
@ -179,6 +179,7 @@ export class NotificationService implements OnApplicationShutdown {
|
|||||||
this.pushNotificationService.pushNotification(notifieeId, 'notification', packed);
|
this.pushNotificationService.pushNotification(notifieeId, 'notification', packed);
|
||||||
|
|
||||||
if (type === 'follow') this.emailNotificationFollow(notifieeId, await this.usersRepository.findOneByOrFail({ id: notifierId! }));
|
if (type === 'follow') this.emailNotificationFollow(notifieeId, await this.usersRepository.findOneByOrFail({ id: notifierId! }));
|
||||||
|
if (type === 'unfollow') this.emailNotificationUnFollow(notifieeId, await this.usersRepository.findOneByOrFail({ id: notifierId! }));
|
||||||
if (type === 'receiveFollowRequest') this.emailNotificationReceiveFollowRequest(notifieeId, await this.usersRepository.findOneByOrFail({ id: notifierId! }));
|
if (type === 'receiveFollowRequest') this.emailNotificationReceiveFollowRequest(notifieeId, await this.usersRepository.findOneByOrFail({ id: notifierId! }));
|
||||||
}, () => { /* aborted, ignore it */ });
|
}, () => { /* aborted, ignore it */ });
|
||||||
|
|
||||||
@ -202,6 +203,18 @@ export class NotificationService implements OnApplicationShutdown {
|
|||||||
*/
|
*/
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@bindThis
|
||||||
|
private async emailNotificationUnFollow(userId: MiUser['id'], follower: MiUser) {
|
||||||
|
/*
|
||||||
|
const userProfile = await UserProfiles.findOneByOrFail({ userId: userId });
|
||||||
|
if (!userProfile.email || !userProfile.emailNotificationTypes.includes('follow')) return;
|
||||||
|
const locale = locales[userProfile.lang ?? 'ja-JP'];
|
||||||
|
const i18n = new I18n(locale);
|
||||||
|
// TODO: render user information html
|
||||||
|
sendEmail(userProfile.email, i18n.t('_email._unfollow.title'), `${follower.name} (@${Acct.toString(follower)})`, `${follower.name} (@${Acct.toString(follower)})`);
|
||||||
|
*/
|
||||||
|
}
|
||||||
|
|
||||||
@bindThis
|
@bindThis
|
||||||
private async emailNotificationReceiveFollowRequest(userId: MiUser['id'], follower: MiUser) {
|
private async emailNotificationReceiveFollowRequest(userId: MiUser['id'], follower: MiUser) {
|
||||||
/*
|
/*
|
||||||
|
@ -431,6 +431,24 @@ export class UserFollowingService implements OnModuleInit {
|
|||||||
const content = this.apRendererService.addContext(this.apRendererService.renderReject(this.apRendererService.renderFollow(follower as MiPartialRemoteUser, followee as MiPartialLocalUser), followee));
|
const content = this.apRendererService.addContext(this.apRendererService.renderReject(this.apRendererService.renderFollow(follower as MiPartialRemoteUser, followee as MiPartialLocalUser), followee));
|
||||||
this.queueService.deliver(followee, content, follower.inbox, false);
|
this.queueService.deliver(followee, content, follower.inbox, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// UnFollow
|
||||||
|
if (this.userEntityService.isLocalUser(followee)) {
|
||||||
|
this.userEntityService.pack(follower.id, followee).then(async packed => {
|
||||||
|
this.globalEventService.publishMainStream(followee.id, 'unfollow', packed);
|
||||||
|
|
||||||
|
const webhooks = (await this.webhookService.getActiveWebhooks()).filter(x => x.userId === followee.id && x.on.includes('unfollow'));
|
||||||
|
for (const webhook of webhooks) {
|
||||||
|
this.queueService.userWebhookDeliver(webhook, 'unfollow', {
|
||||||
|
user: packed,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// 通知を作成
|
||||||
|
this.notificationService.createNotification(followee.id, 'unfollow', {
|
||||||
|
}, follower.id);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@bindThis
|
@bindThis
|
||||||
|
@ -19,6 +19,11 @@ export type MiNotification = {
|
|||||||
id: string;
|
id: string;
|
||||||
createdAt: string;
|
createdAt: string;
|
||||||
notifierId: MiUser['id'];
|
notifierId: MiUser['id'];
|
||||||
|
} | {
|
||||||
|
type: 'unfollow';
|
||||||
|
id: string;
|
||||||
|
createdAt: string;
|
||||||
|
notifierId: MiUser['id'];
|
||||||
} | {
|
} | {
|
||||||
type: 'mention';
|
type: 'mention';
|
||||||
id: string;
|
id: string;
|
||||||
|
@ -6,6 +6,7 @@
|
|||||||
/**
|
/**
|
||||||
* note - 通知オンにしているユーザーが投稿した
|
* note - 通知オンにしているユーザーが投稿した
|
||||||
* follow - フォローされた
|
* follow - フォローされた
|
||||||
|
* unfollow - フォロー解除された
|
||||||
* mention - 投稿で自分が言及された
|
* mention - 投稿で自分が言及された
|
||||||
* reply - 投稿に返信された
|
* reply - 投稿に返信された
|
||||||
* renote - 投稿がRenoteされた
|
* renote - 投稿がRenoteされた
|
||||||
@ -22,6 +23,7 @@
|
|||||||
export const notificationTypes = [
|
export const notificationTypes = [
|
||||||
'note',
|
'note',
|
||||||
'follow',
|
'follow',
|
||||||
|
'unfollow',
|
||||||
'mention',
|
'mention',
|
||||||
'reply',
|
'reply',
|
||||||
'renote',
|
'renote',
|
||||||
|
@ -17,6 +17,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||||||
<div
|
<div
|
||||||
:class="[$style.subIcon, {
|
:class="[$style.subIcon, {
|
||||||
[$style.t_follow]: notification.type === 'follow',
|
[$style.t_follow]: notification.type === 'follow',
|
||||||
|
[$style.t_unfollow]: notification.type === 'unfollow',
|
||||||
[$style.t_followRequestAccepted]: notification.type === 'followRequestAccepted',
|
[$style.t_followRequestAccepted]: notification.type === 'followRequestAccepted',
|
||||||
[$style.t_receiveFollowRequest]: notification.type === 'receiveFollowRequest',
|
[$style.t_receiveFollowRequest]: notification.type === 'receiveFollowRequest',
|
||||||
[$style.t_renote]: notification.type === 'renote',
|
[$style.t_renote]: notification.type === 'renote',
|
||||||
@ -30,6 +31,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||||||
}]"
|
}]"
|
||||||
> <!-- we re-use t_pollEnded for "edited" instead of making an identical style -->
|
> <!-- we re-use t_pollEnded for "edited" instead of making an identical style -->
|
||||||
<i v-if="notification.type === 'follow'" class="ti ti-plus"></i>
|
<i v-if="notification.type === 'follow'" class="ti ti-plus"></i>
|
||||||
|
<i v-else-if="notification.type === 'unfollow'" class="ti ti-minus"></i>
|
||||||
<i v-else-if="notification.type === 'receiveFollowRequest'" class="ti ti-clock"></i>
|
<i v-else-if="notification.type === 'receiveFollowRequest'" class="ti ti-clock"></i>
|
||||||
<i v-else-if="notification.type === 'followRequestAccepted'" class="ti ti-check"></i>
|
<i v-else-if="notification.type === 'followRequestAccepted'" class="ti ti-check"></i>
|
||||||
<i v-else-if="notification.type === 'renote'" class="ti ti-repeat"></i>
|
<i v-else-if="notification.type === 'renote'" class="ti ti-repeat"></i>
|
||||||
@ -60,7 +62,8 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||||||
<span v-else-if="notification.type === 'roleAssigned'">{{ i18n.ts._notification.roleAssigned }}</span>
|
<span v-else-if="notification.type === 'roleAssigned'">{{ i18n.ts._notification.roleAssigned }}</span>
|
||||||
<span v-else-if="notification.type === 'achievementEarned'">{{ i18n.ts._notification.achievementEarned }}</span>
|
<span v-else-if="notification.type === 'achievementEarned'">{{ i18n.ts._notification.achievementEarned }}</span>
|
||||||
<span v-else-if="notification.type === 'test'">{{ i18n.ts._notification.testNotification }}</span>
|
<span v-else-if="notification.type === 'test'">{{ i18n.ts._notification.testNotification }}</span>
|
||||||
<MkA v-else-if="notification.type === 'follow' || notification.type === 'mention' || notification.type === 'reply' || notification.type === 'renote' || notification.type === 'quote' || notification.type === 'reaction' || notification.type === 'receiveFollowRequest' || notification.type === 'followRequestAccepted'" v-user-preview="notification.user.id" :class="$style.headerName" :to="userPage(notification.user)"><MkUserName :user="notification.user"/></MkA>
|
<span v-else-if="notification.type === 'exportCompleted'">{{ i18n.tsx._notification.exportOfXCompleted({ x: exportEntityName[notification.exportedEntity] }) }}</span>
|
||||||
|
<MkA v-else-if="notification.type === 'follow' || notification.type === 'unfollow' || notification.type === 'mention' || notification.type === 'reply' || notification.type === 'renote' || notification.type === 'quote' || notification.type === 'reaction' || notification.type === 'receiveFollowRequest' || notification.type === 'followRequestAccepted'" v-user-preview="notification.user.id" :class="$style.headerName" :to="userPage(notification.user)"><MkUserName :user="notification.user"/></MkA>
|
||||||
<span v-else-if="notification.type === 'reaction:grouped' && notification.note.reactionAcceptance === 'likeOnly'">{{ i18n.tsx._notification.likedBySomeUsers({ n: getActualReactedUsersCount(notification) }) }}</span>
|
<span v-else-if="notification.type === 'reaction:grouped' && notification.note.reactionAcceptance === 'likeOnly'">{{ i18n.tsx._notification.likedBySomeUsers({ n: getActualReactedUsersCount(notification) }) }}</span>
|
||||||
<span v-else-if="notification.type === 'reaction:grouped'">{{ i18n.tsx._notification.reactedBySomeUsers({ n: getActualReactedUsersCount(notification) }) }}</span>
|
<span v-else-if="notification.type === 'reaction:grouped'">{{ i18n.tsx._notification.reactedBySomeUsers({ n: getActualReactedUsersCount(notification) }) }}</span>
|
||||||
<span v-else-if="notification.type === 'renote:grouped'">{{ i18n.tsx._notification.renotedBySomeUsers({ n: notification.users.length }) }}</span>
|
<span v-else-if="notification.type === 'renote:grouped'">{{ i18n.tsx._notification.renotedBySomeUsers({ n: notification.users.length }) }}</span>
|
||||||
@ -106,6 +109,10 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||||||
<span :class="$style.text" style="opacity: 0.6;">{{ i18n.ts.youGotNewFollower }}</span>
|
<span :class="$style.text" style="opacity: 0.6;">{{ i18n.ts.youGotNewFollower }}</span>
|
||||||
</template>
|
</template>
|
||||||
<span v-else-if="notification.type === 'followRequestAccepted'" :class="$style.text" style="opacity: 0.6;">{{ i18n.ts.followRequestAccepted }}</span>
|
<span v-else-if="notification.type === 'followRequestAccepted'" :class="$style.text" style="opacity: 0.6;">{{ i18n.ts.followRequestAccepted }}</span>
|
||||||
|
<template v-else-if="notification.type === 'unfollow'">
|
||||||
|
<span :class="$style.text" style="opacity: 0.6;">{{ i18n.ts.youGotUnFollower }}</span>
|
||||||
|
<div v-if="full"><MkFollowButton :user="notification.user" :full="true"/></div>
|
||||||
|
</template>
|
||||||
<template v-else-if="notification.type === 'receiveFollowRequest'">
|
<template v-else-if="notification.type === 'receiveFollowRequest'">
|
||||||
<span :class="$style.text" style="opacity: 0.6;">{{ i18n.ts.receiveFollowRequest }}</span>
|
<span :class="$style.text" style="opacity: 0.6;">{{ i18n.ts.receiveFollowRequest }}</span>
|
||||||
<div v-if="full && !followRequestDone" :class="$style.followRequestCommands">
|
<div v-if="full && !followRequestDone" :class="$style.followRequestCommands">
|
||||||
@ -200,6 +207,7 @@ function getActualReactedUsersCount(notification: Misskey.entities.Notification)
|
|||||||
overflow-wrap: break-word;
|
overflow-wrap: break-word;
|
||||||
display: flex;
|
display: flex;
|
||||||
contain: content;
|
contain: content;
|
||||||
|
--eventUnFollow: #f08080;
|
||||||
}
|
}
|
||||||
|
|
||||||
.head {
|
.head {
|
||||||
@ -272,6 +280,12 @@ function getActualReactedUsersCount(notification: Misskey.entities.Notification)
|
|||||||
pointer-events: none;
|
pointer-events: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.t_unfollow {
|
||||||
|
padding: 3px;
|
||||||
|
background: var(--eventUnFollow);
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
|
||||||
.t_renote {
|
.t_renote {
|
||||||
padding: 3px;
|
padding: 3px;
|
||||||
background: var(--eventRenote);
|
background: var(--eventRenote);
|
||||||
|
@ -108,6 +108,7 @@ https://developer.mozilla.org/en-US/docs/Web/Media/Formats/Containers
|
|||||||
export const notificationTypes = [
|
export const notificationTypes = [
|
||||||
'note',
|
'note',
|
||||||
'follow',
|
'follow',
|
||||||
|
'unfollow',
|
||||||
'mention',
|
'mention',
|
||||||
'reply',
|
'reply',
|
||||||
'renote',
|
'renote',
|
||||||
|
@ -36,6 +36,9 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||||||
<MkSwitch v-model="emailNotification_follow">
|
<MkSwitch v-model="emailNotification_follow">
|
||||||
{{ i18n.ts._notification._types.follow }}
|
{{ i18n.ts._notification._types.follow }}
|
||||||
</MkSwitch>
|
</MkSwitch>
|
||||||
|
<MkSwitch v-model="emailNotification_unfollow">
|
||||||
|
{{ i18n.ts._notification._types.unfollow }}
|
||||||
|
</MkSwitch>
|
||||||
<MkSwitch v-model="emailNotification_receiveFollowRequest">
|
<MkSwitch v-model="emailNotification_receiveFollowRequest">
|
||||||
{{ i18n.ts._notification._types.receiveFollowRequest }}
|
{{ i18n.ts._notification._types.receiveFollowRequest }}
|
||||||
</MkSwitch>
|
</MkSwitch>
|
||||||
@ -85,6 +88,7 @@ const emailNotification_mention = ref($i.emailNotificationTypes.includes('mentio
|
|||||||
const emailNotification_reply = ref($i.emailNotificationTypes.includes('reply'));
|
const emailNotification_reply = ref($i.emailNotificationTypes.includes('reply'));
|
||||||
const emailNotification_quote = ref($i.emailNotificationTypes.includes('quote'));
|
const emailNotification_quote = ref($i.emailNotificationTypes.includes('quote'));
|
||||||
const emailNotification_follow = ref($i.emailNotificationTypes.includes('follow'));
|
const emailNotification_follow = ref($i.emailNotificationTypes.includes('follow'));
|
||||||
|
const emailNotification_unfollow = ref($i.emailNotificationTypes.includes('unfollow'))
|
||||||
const emailNotification_receiveFollowRequest = ref($i.emailNotificationTypes.includes('receiveFollowRequest'));
|
const emailNotification_receiveFollowRequest = ref($i.emailNotificationTypes.includes('receiveFollowRequest'));
|
||||||
|
|
||||||
const saveNotificationSettings = () => {
|
const saveNotificationSettings = () => {
|
||||||
@ -94,12 +98,13 @@ const saveNotificationSettings = () => {
|
|||||||
...[emailNotification_reply.value ? 'reply' : null],
|
...[emailNotification_reply.value ? 'reply' : null],
|
||||||
...[emailNotification_quote.value ? 'quote' : null],
|
...[emailNotification_quote.value ? 'quote' : null],
|
||||||
...[emailNotification_follow.value ? 'follow' : null],
|
...[emailNotification_follow.value ? 'follow' : null],
|
||||||
|
...[emailNotification_unfollow.value ? 'unfollow' : null],
|
||||||
...[emailNotification_receiveFollowRequest.value ? 'receiveFollowRequest' : null],
|
...[emailNotification_receiveFollowRequest.value ? 'receiveFollowRequest' : null],
|
||||||
].filter(x => x != null),
|
].filter(x => x != null),
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
watch([emailNotification_mention, emailNotification_reply, emailNotification_quote, emailNotification_follow, emailNotification_receiveFollowRequest], () => {
|
watch([emailNotification_mention, emailNotification_reply, emailNotification_quote, emailNotification_follow, emailNotification_unfollow,emailNotification_receiveFollowRequest], () => {
|
||||||
saveNotificationSettings();
|
saveNotificationSettings();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -72,6 +72,25 @@ async function composeNotification(data: PushNotificationDataMap[keyof PushNotif
|
|||||||
}];
|
}];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
case 'unfollow': {
|
||||||
|
// フォローが外されたときの処理
|
||||||
|
const account = await getAccountFromId(data.userId);
|
||||||
|
if (!account) return null;
|
||||||
|
const userDetail = await cli.request('users/show', { userId: data.body.userId }, account.token);
|
||||||
|
return [i18n.ts._notification.youWereUnFollower, {
|
||||||
|
body: getUserName(data.body.user),
|
||||||
|
icon: data.body.user.avatarUrl ?? undefined,
|
||||||
|
badge: iconUrl('user-minus'),
|
||||||
|
data,
|
||||||
|
actions: userDetail.isFollowing ? [] : [
|
||||||
|
{
|
||||||
|
action: 'follow',
|
||||||
|
title: i18n.ts._notification._actions.followBack,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}];
|
||||||
|
}
|
||||||
|
|
||||||
case 'mention':
|
case 'mention':
|
||||||
return [t('_notification.youGotMention', { name: getUserName(data.body.user) }), {
|
return [t('_notification.youGotMention', { name: getUserName(data.body.user) }), {
|
||||||
body: data.body.note.text ?? '',
|
body: data.body.note.text ?? '',
|
||||||
|
Loading…
Reference in New Issue
Block a user