diff --git a/CHANGELOG.md b/CHANGELOG.md index 698b4acead..ee2f11b156 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,6 +12,19 @@ --> +## 2023.9.3 +### General +- Enhance: ノートの翻訳機能の利用可否をロールで設定可能に + +### Client +- Enhance: AiScriptでホストのアドレスを参照する定数`SERVER_URL`を追加 +- Enhance: モデレーションログ機能の強化 +- Enhance: ローカリゼーションの更新 + +### Server +- Fix: Redisに古いバージョンのキャッシュが残っている場合、キャッシュが消えるまでの間通知が届かなくなる問題を修正 +- Fix: 後方互換性の修正 + ## 2023.9.2 ### General diff --git a/locales/de-DE.yml b/locales/de-DE.yml index cc41c31310..f382ddbe18 100644 --- a/locales/de-DE.yml +++ b/locales/de-DE.yml @@ -1123,6 +1123,9 @@ authenticationRequiredToContinue: "Bitte authentifiziere dich, um fortzufahren" dateAndTime: "Zeit" showRenotes: "Renotes anzeigen" edited: "Bearbeitet" +notificationRecieveConfig: "Benachrichtigungseinstellungen" +mutualFollow: "Gegenseitig gefolgt" +fileAttachedOnly: "Nur Notizen mit Dateien" _announcement: forExistingUsers: "Nur für existierende Nutzer" forExistingUsersDescription: "Ist diese Option aktiviert, wird diese Ankündigung nur Nutzern angezeigt, die zum Zeitpunkt der Ankündigung bereits registriert sind. Ist sie deaktiviert, wird sie auch Nutzern, die sich nach dessen Veröffentlichung registrieren, angezeigt." @@ -2132,3 +2135,6 @@ _moderationLogTypes: unmarkSensitiveDriveFile: "Datei als nicht sensitiv markiert" resolveAbuseReport: "Meldung bearbeitet" createInvitation: "Einladung erstellt" + createAd: "Werbung erstellt" + deleteAd: "Werbung gelöscht" + updateAd: "Werbung aktualisiert" diff --git a/locales/en-US.yml b/locales/en-US.yml index f40b40a3ee..e66cbaf913 100644 --- a/locales/en-US.yml +++ b/locales/en-US.yml @@ -1125,6 +1125,9 @@ authenticationRequiredToContinue: "Please authenticate to continue" dateAndTime: "Timestamp" showRenotes: "Show renotes" edited: "Edited" +notificationRecieveConfig: "Notification Settings" +mutualFollow: "Mutual follow" +fileAttachedOnly: "Only notes with files" _announcement: forExistingUsers: "Existing users only" forExistingUsersDescription: "This announcement will only be shown to users existing at the point of publishment if enabled. If disabled, those newly signing up after it has been posted will also see it." @@ -2138,3 +2141,6 @@ _moderationLogTypes: unmarkSensitiveDriveFile: "File unmarked as sensitive" resolveAbuseReport: "Report resolved" createInvitation: "Invite generated" + createAd: "Ad created" + deleteAd: "Ad deleted" + updateAd: "Ad updated" diff --git a/locales/index.d.ts b/locales/index.d.ts index cb18076bbc..8eb8c4429e 100644 --- a/locales/index.d.ts +++ b/locales/index.d.ts @@ -1568,6 +1568,7 @@ export interface Locale { "descriptionOfRateLimitFactor": string; "canHideAds": string; "canSearchNotes": string; + "canUseTranslator": string; }; "_condition": { "isLocal": string; diff --git a/locales/ja-JP.yml b/locales/ja-JP.yml index ded307dcf4..a761ce6477 100644 --- a/locales/ja-JP.yml +++ b/locales/ja-JP.yml @@ -1488,7 +1488,8 @@ _role: rateLimitFactor: "レートリミット" descriptionOfRateLimitFactor: "小さいほど制限が緩和され、大きいほど制限が強化されます。" canHideAds: "広告の非表示" - canSearchNotes: "ノート検索の利用可否" + canSearchNotes: "ノート検索の利用" + canUseTranslator: "翻訳機能の利用" _condition: isLocal: "ローカルユーザー" isRemote: "リモートユーザー" diff --git a/locales/ko-KR.yml b/locales/ko-KR.yml index db5cfa9cf6..fa1bb446c4 100644 --- a/locales/ko-KR.yml +++ b/locales/ko-KR.yml @@ -416,6 +416,9 @@ totp: "인증 앱" totpDescription: "인증 앱을 사용하여 일회성 비밀번호 입력" moderator: "모더레이터" moderation: "모더레이션" +moderationNote: "모더레이션 노트" +addModerationNote: "모더레이션 노트 추가하기" +moderationLogs: "모더레이션 로그" nUsersMentioned: "{n}명이 언급함" securityKeyAndPasskey: "보안 키 또는 패스 키" securityKey: "보안 키" @@ -1107,6 +1110,18 @@ youHaveUnreadAnnouncements: "읽지 않은 공지사항이 있습니다." useSecurityKey: "브라우저 또는 기기의 안내에 따라 보안 키 또는 패스키를 사용해 주십시오." replies: "답글" renotes: "리노트" +loadReplies: "답글 보기" +loadConversation: "대화 보기" +pinnedList: "고정해놓은 리스트" +keepScreenOn: "기기 화면을 항상 켜기" +verifiedLink: "이 링크의 소유자임이 확인되었습니다." +notifyNotes: "새 노트 알림 켜기" +unnotifyNotes: "새 노트 알림 끄기" +authentication: "인증" +showRenotes: "리노트 표시" +edited: "수정됨" +notificationRecieveConfig: "알림 설정" +mutualFollow: "맞팔로우" _announcement: forExistingUsers: "기존 유저에게만 알림" forExistingUsersDescription: "활성화하면 이 공지사항을 게시한 시점에서 이미 가입한 유저에게만 표시합니다. 비활성화하면 게시 후에 가입한 유저에게도 표시합니다." @@ -1135,6 +1150,12 @@ _serverRules: description: "회원 가입 이전에 간단하게 표시할 서버 규칙입니다. 이용 약관의 요약으로 구성하는 것을 추천합니다." _serverSettings: iconUrl: "아이콘 URL" + appIconUsageExample: "예를 들어, PWA나 스마트폰 홈 화면에 북마크로 추가되었을 때 등" + appIconStyleRecommendation: "아이콘이 원형 또는 둥근 사각형으로 잘리는 경우가 있으므로, 가장자리 여백이 충분한 사진을 사용하는 것을 추천합니다." + appIconResolutionMustBe: "해상도는 반드시 {resolution} 이어야 합니다." + manifestJsonOverride: "manifest.json 오버라이드" + shortName: "약칭" + shortNameDescription: "서버의 정식 명칭이 긴 경우에, 대신에 표시할 수 있는 약칭이나 통칭." _accountMigration: moveFrom: "다른 계정에서 이 계정으로 이사" moveFromSub: "다른 계정에 대한 별칭을 생성" diff --git a/locales/th-TH.yml b/locales/th-TH.yml index 307ff757f4..b1526f86cc 100644 --- a/locales/th-TH.yml +++ b/locales/th-TH.yml @@ -1120,6 +1120,9 @@ authentication: "การตรวจสอบสิทธิ์" dateAndTime: "เวลาประทับ" showRenotes: "แสดงรีโน้ต" edited: "แก้ไขแล้ว" +notificationRecieveConfig: "การตั้งค่าการแจ้งเตือน" +mutualFollow: "ติดตามซึ่งกันและกัน" +fileAttachedOnly: "เฉพาะโน้ตที่มีไฟล์เท่านั้น" _announcement: forExistingUsers: "ผู้ใช้งานที่มีอยู่เท่านั้น" forExistingUsersDescription: "การประกาศนี้จะแสดงต่อผู้ใช้ที่มีอยู่ ณ จุดที่เผยแพร่นั้นๆถ้าหากเปิดใช้งาน ถ้าหากปิดใช้งานผู้ที่กำลังสมัครใหม่หลังจากโพสต์แล้วนั้นก็จะเห็นเช่นกัน" @@ -2104,3 +2107,6 @@ _moderationLogTypes: resetPassword: "รีเซ็ตรหัสผ่าน" resolveAbuseReport: "รายงานได้รับการแก้ไขแล้ว" createInvitation: "สร้างคำเชิญ" + createAd: "สร้างโฆษณาแล้ว" + deleteAd: "ลบโฆษณาออกแล้ว" + updateAd: "อัปเดตโฆษณาแล้ว" diff --git a/locales/zh-CN.yml b/locales/zh-CN.yml index 4348b78ae7..5b48356dba 100644 --- a/locales/zh-CN.yml +++ b/locales/zh-CN.yml @@ -1123,6 +1123,9 @@ authenticationRequiredToContinue: "要继续,请先进行验证" dateAndTime: "日期和时间" showRenotes: "显示转帖" edited: "已编辑" +notificationRecieveConfig: "通知接收设置" +mutualFollow: "互相关注" +fileAttachedOnly: "仅限媒体" _announcement: forExistingUsers: "仅限现有用户" forExistingUsersDescription: "若启用,该公告将仅对创建此公告时存在的用户可见。 如果禁用,则在创建此公告后注册的用户也可以看到该公告。" @@ -2130,3 +2133,6 @@ _moderationLogTypes: unmarkSensitiveDriveFile: "取消标记网盘文件为敏感媒体" resolveAbuseReport: "处理举报" createInvitation: "发行邀请码" + createAd: "创建了广告" + deleteAd: "删除了广告" + updateAd: "更新了广告" diff --git a/locales/zh-TW.yml b/locales/zh-TW.yml index 9f90eaaa66..9f695fc108 100644 --- a/locales/zh-TW.yml +++ b/locales/zh-TW.yml @@ -1122,6 +1122,8 @@ authentication: "驗證" authenticationRequiredToContinue: "請於繼續前完成驗證" dateAndTime: "日期與時間" showRenotes: "顯示轉發貼文" +edited: "已編輯" +mutualFollow: "互相追隨" _announcement: forExistingUsers: "僅限既有的使用者" forExistingUsersDescription: "啟用代表僅向現存使用者顯示;停用代表張貼後註冊的新使用者也會看到。" @@ -2131,3 +2133,6 @@ _moderationLogTypes: unmarkSensitiveDriveFile: "撤銷標記為敏感檔案" resolveAbuseReport: "解決檢舉" createInvitation: "建立邀請碼" + createAd: "建立廣告" + deleteAd: "刪除廣告" + updateAd: "更新廣告" diff --git a/package.json b/package.json index 9e3131e472..254303324d 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "misskey", - "version": "2023.9.2-io", + "version": "2023.9.3-io", "codename": "nasubi", "repository": { "type": "git", diff --git a/packages/backend/src/core/NotificationService.ts b/packages/backend/src/core/NotificationService.ts index ba8798f181..ca05989a4a 100644 --- a/packages/backend/src/core/NotificationService.ts +++ b/packages/backend/src/core/NotificationService.ts @@ -80,7 +80,10 @@ export class NotificationService implements OnApplicationShutdown { notifierId?: MiUser['id'] | null, ): Promise { const profile = await this.cacheService.userProfileCache.fetch(notifieeId); - const recieveConfig = profile.notificationRecieveConfig[type]; + + // 古いMisskeyバージョンのキャッシュが残っている可能性がある + // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition + const recieveConfig = (profile.notificationRecieveConfig ?? {})[type]; if (recieveConfig?.type === 'never') { return null; } diff --git a/packages/backend/src/core/RoleService.ts b/packages/backend/src/core/RoleService.ts index 053eae6e93..dbfdba2dae 100644 --- a/packages/backend/src/core/RoleService.ts +++ b/packages/backend/src/core/RoleService.ts @@ -36,6 +36,7 @@ export type RolePolicies = { inviteExpirationTime: number; canManageCustomEmojis: boolean; canSearchNotes: boolean; + canUseTranslator: boolean; canHideAds: boolean; driveCapacityMb: number; alwaysMarkNsfw: boolean; @@ -64,6 +65,7 @@ export const DEFAULT_POLICIES: RolePolicies = { inviteExpirationTime: 0, canManageCustomEmojis: false, canSearchNotes: false, + canUseTranslator: true, canHideAds: false, driveCapacityMb: 100, alwaysMarkNsfw: false, @@ -312,6 +314,7 @@ export class RoleService implements OnApplicationShutdown { inviteExpirationTime: calc('inviteExpirationTime', vs => Math.max(...vs)), canManageCustomEmojis: calc('canManageCustomEmojis', vs => vs.some(v => v === true)), canSearchNotes: calc('canSearchNotes', vs => vs.some(v => v === true)), + canUseTranslator: calc('canUseTranslator', vs => vs.some(v => v === true)), canHideAds: calc('canHideAds', vs => vs.some(v => v === true)), driveCapacityMb: calc('driveCapacityMb', vs => Math.max(...vs)), alwaysMarkNsfw: calc('alwaysMarkNsfw', vs => vs.some(v => v === true)), diff --git a/packages/backend/src/core/entities/UserEntityService.ts b/packages/backend/src/core/entities/UserEntityService.ts index 84e2df7ec5..4678aa93d1 100644 --- a/packages/backend/src/core/entities/UserEntityService.ts +++ b/packages/backend/src/core/entities/UserEntityService.ts @@ -456,6 +456,7 @@ export class UserEntityService implements OnModuleInit { hasPendingReceivedFollowRequest: this.getHasPendingReceivedFollowRequest(user.id), mutedWords: profile!.mutedWords, mutedInstances: profile!.mutedInstances, + mutingNotificationTypes: [], // 後方互換性のため notificationRecieveConfig: profile!.notificationRecieveConfig, emailNotificationTypes: profile!.emailNotificationTypes, achievements: profile!.achievements, diff --git a/packages/backend/src/server/api/endpoints/notes/translate.ts b/packages/backend/src/server/api/endpoints/notes/translate.ts index 00cb9a0a28..a1561c944c 100644 --- a/packages/backend/src/server/api/endpoints/notes/translate.ts +++ b/packages/backend/src/server/api/endpoints/notes/translate.ts @@ -10,12 +10,13 @@ import { NoteEntityService } from '@/core/entities/NoteEntityService.js'; import { MetaService } from '@/core/MetaService.js'; import { HttpRequestService } from '@/core/HttpRequestService.js'; import { GetterService } from '@/server/api/GetterService.js'; +import { RoleService } from '@/core/RoleService.js'; import { ApiError } from '../../error.js'; export const meta = { tags: ['notes'], - requireCredential: false, + requireCredential: true, res: { type: 'object', @@ -23,6 +24,11 @@ export const meta = { }, errors: { + unavailable: { + message: 'Translate of notes unavailable.', + code: 'UNAVAILABLE', + id: '50a70314-2d8a-431b-b433-efa5cc56444c', + }, noSuchNote: { message: 'No such note.', code: 'NO_SUCH_NOTE', @@ -47,14 +53,20 @@ export default class extends Endpoint { // eslint- private getterService: GetterService, private metaService: MetaService, private httpRequestService: HttpRequestService, + private roleService: RoleService, ) { super(meta, paramDef, async (ps, me) => { + const policies = await this.roleService.getUserPolicies(me.id); + if (!policies.canUseTranslator) { + throw new ApiError(meta.errors.unavailable); + } + const note = await this.getterService.getNote(ps.noteId).catch(err => { if (err.id === '9725d0ce-ba28-4dde-95a7-2cbb2c15de24') throw new ApiError(meta.errors.noSuchNote); throw err; }); - if (!(await this.noteEntityService.isVisibleForMe(note, me ? me.id : null))) { + if (!(await this.noteEntityService.isVisibleForMe(note, me.id))) { return 204; // TODO: 良い感じのエラー返す } diff --git a/packages/backend/test/e2e/users.ts b/packages/backend/test/e2e/users.ts index a91affcea7..16c30f2bf9 100644 --- a/packages/backend/test/e2e/users.ts +++ b/packages/backend/test/e2e/users.ts @@ -167,6 +167,7 @@ describe('ユーザー', () => { unreadAnnouncements: user.unreadAnnouncements, mutedWords: user.mutedWords, mutedInstances: user.mutedInstances, + mutingNotificationTypes: user.mutingNotificationTypes, notificationRecieveConfig: user.notificationRecieveConfig, emailNotificationTypes: user.emailNotificationTypes, achievements: user.achievements, @@ -416,6 +417,7 @@ describe('ユーザー', () => { assert.deepStrictEqual(response.unreadAnnouncements, []); assert.deepStrictEqual(response.mutedWords, []); assert.deepStrictEqual(response.mutedInstances, []); + assert.deepStrictEqual(response.mutingNotificationTypes, []); assert.deepStrictEqual(response.notificationRecieveConfig, {}); assert.deepStrictEqual(response.emailNotificationTypes, ['follow', 'receiveFollowRequest']); assert.deepStrictEqual(response.achievements, []); diff --git a/packages/frontend/src/const.ts b/packages/frontend/src/const.ts index da3ef1e975..8e14c07c01 100644 --- a/packages/frontend/src/const.ts +++ b/packages/frontend/src/const.ts @@ -71,6 +71,7 @@ export const ROLE_POLICIES = [ 'inviteExpirationTime', 'canManageCustomEmojis', 'canSearchNotes', + 'canUseTranslator', 'canHideAds', 'driveCapacityMb', 'alwaysMarkNsfw', diff --git a/packages/frontend/src/pages/admin/modlog.ModLog.vue b/packages/frontend/src/pages/admin/modlog.ModLog.vue index 99b8544f33..66561c969e 100644 --- a/packages/frontend/src/pages/admin/modlog.ModLog.vue +++ b/packages/frontend/src/pages/admin/modlog.ModLog.vue @@ -17,8 +17,8 @@ SPDX-License-Identifier: AGPL-3.0-only : @{{ log.info.userUsername }}{{ log.info.userHost ? '@' + log.info.userHost : '' }} : @{{ log.info.userUsername }}{{ log.info.userHost ? '@' + log.info.userHost : '' }} : @{{ log.info.userUsername }}{{ log.info.userHost ? '@' + log.info.userHost : '' }} - : @{{ log.info.userUsername }}{{ log.info.userHost ? '@' + log.info.userHost : '' }} - : @{{ log.info.userUsername }}{{ log.info.userHost ? '@' + log.info.userHost : '' }} + : @{{ log.info.userUsername }}{{ log.info.userHost ? '@' + log.info.userHost : '' }} {{ log.info.roleName }} + : @{{ log.info.userUsername }}{{ log.info.userHost ? '@' + log.info.userHost : '' }} {{ log.info.roleName }} : {{ log.info.role.name }} : {{ log.info.before.name }} : {{ log.info.role.name }} diff --git a/packages/frontend/src/pages/admin/roles.editor.vue b/packages/frontend/src/pages/admin/roles.editor.vue index 9083e5ce52..d5c3a216a4 100644 --- a/packages/frontend/src/pages/admin/roles.editor.vue +++ b/packages/frontend/src/pages/admin/roles.editor.vue @@ -359,6 +359,26 @@ SPDX-License-Identifier: AGPL-3.0-only + + + +
+ + + + + + + + + +
+
+