diff --git a/packages/frontend/src/account.ts b/packages/frontend/src/account.ts index 1e5f38cf1c..25af298910 100644 --- a/packages/frontend/src/account.ts +++ b/packages/frontend/src/account.ts @@ -26,6 +26,11 @@ export const $i = accountData ? reactive(JSON.parse(accountData) as Account) : n export const iAmModerator = $i != null && ($i.isAdmin === true || $i.isModerator === true); export const iAmAdmin = $i != null && $i.isAdmin; +export function signinRequired() { + if ($i == null) throw new Error('signin required'); + return $i; +} + export let notesCount = $i == null ? 0 : $i.notesCount; export function incNotesCount() { notesCount++; diff --git a/packages/frontend/src/pages/my-lists/index.vue b/packages/frontend/src/pages/my-lists/index.vue index 0abfb15d98..14e2315843 100644 --- a/packages/frontend/src/pages/my-lists/index.vue +++ b/packages/frontend/src/pages/my-lists/index.vue @@ -19,7 +19,7 @@ SPDX-License-Identifier: AGPL-3.0-only <div v-if="items.length > 0" class="_gaps"> <MkA v-for="list in items" :key="list.id" class="_panel" :class="$style.list" :to="`/my/lists/${ list.id }`"> - <div style="margin-bottom: 4px;">{{ list.name }} <span :class="$style.nUsers">({{ i18n.t('nUsers', { n: `${list.userIds.length}/${$i?.policies['userEachUserListsLimit']}` }) }})</span></div> + <div style="margin-bottom: 4px;">{{ list.name }} <span :class="$style.nUsers">({{ i18n.t('nUsers', { n: `${list.userIds.length}/${$i.policies['userEachUserListsLimit']}` }) }})</span></div> <MkAvatars :userIds="list.userIds" :limit="10"/> </MkA> </div> @@ -37,7 +37,9 @@ import { i18n } from '@/i18n.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; import { userListsCache } from '@/cache.js'; import { infoImageUrl } from '@/instance.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; + +const $i = signinRequired(); const items = computed(() => userListsCache.value.value ?? []); diff --git a/packages/frontend/src/pages/my-lists/list.vue b/packages/frontend/src/pages/my-lists/list.vue index cf9da02868..482fdcd8f2 100644 --- a/packages/frontend/src/pages/my-lists/list.vue +++ b/packages/frontend/src/pages/my-lists/list.vue @@ -25,7 +25,7 @@ SPDX-License-Identifier: AGPL-3.0-only <MkFolder defaultOpen> <template #label>{{ i18n.ts.members }}</template> - <template #caption>{{ i18n.t('nUsers', { n: `${list.userIds.length}/${$i?.policies['userEachUserListsLimit']}` }) }}</template> + <template #caption>{{ i18n.t('nUsers', { n: `${list.userIds.length}/${$i.policies['userEachUserListsLimit']}` }) }}</template> <div class="_gaps_s"> <MkButton rounded primary style="margin: 0 auto;" @click="addUser()">{{ i18n.ts.addUser }}</MkButton> @@ -66,10 +66,12 @@ import MkSwitch from '@/components/MkSwitch.vue'; import MkFolder from '@/components/MkFolder.vue'; import MkInput from '@/components/MkInput.vue'; import { userListsCache } from '@/cache.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { defaultStore } from '@/store.js'; import MkPagination from '@/components/MkPagination.vue'; +const $i = signinRequired(); + const { enableInfiniteScroll, } = defaultStore.reactiveState; diff --git a/packages/frontend/src/pages/settings/2fa.qrdialog.vue b/packages/frontend/src/pages/settings/2fa.qrdialog.vue index 4641b49103..3d7bb06da2 100644 --- a/packages/frontend/src/pages/settings/2fa.qrdialog.vue +++ b/packages/frontend/src/pages/settings/2fa.qrdialog.vue @@ -110,7 +110,9 @@ import * as os from '@/os.js'; import MkFolder from '@/components/MkFolder.vue'; import MkInfo from '@/components/MkInfo.vue'; import { confetti } from '@/scripts/confetti.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; + +const $i = signinRequired(); defineProps<{ twoFactorData: { @@ -151,7 +153,7 @@ function downloadBackupCodes() { const txtBlob = new Blob([backupCodes.value.join('\n')], { type: 'text/plain' }); const dummya = document.createElement('a'); dummya.href = URL.createObjectURL(txtBlob); - dummya.download = `${$i?.username}-2fa-backup-codes.txt`; + dummya.download = `${$i.username}-2fa-backup-codes.txt`; dummya.click(); } } diff --git a/packages/frontend/src/pages/settings/2fa.vue b/packages/frontend/src/pages/settings/2fa.vue index 4c165ef4ee..35331738fd 100644 --- a/packages/frontend/src/pages/settings/2fa.vue +++ b/packages/frontend/src/pages/settings/2fa.vue @@ -80,9 +80,11 @@ import MkSwitch from '@/components/MkSwitch.vue'; import FormSection from '@/components/form/section.vue'; import MkFolder from '@/components/MkFolder.vue'; import * as os from '@/os.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { i18n } from '@/i18n.js'; +const $i = signinRequired(); + // メモ: 各エンドポイントはmeUpdatedを発行するため、refreshAccountは不要 withDefaults(defineProps<{ @@ -91,7 +93,7 @@ withDefaults(defineProps<{ first: false, }); -const usePasswordLessLogin = computed(() => $i?.usePasswordLessLogin ?? false); +const usePasswordLessLogin = computed(() => $i.usePasswordLessLogin ?? false); async function registerTOTP(): Promise<void> { const auth = await os.authenticateDialog(); diff --git a/packages/frontend/src/pages/settings/avatar-decoration.decoration.vue b/packages/frontend/src/pages/settings/avatar-decoration.decoration.vue index 9c95b5547e..29586ad5f1 100644 --- a/packages/frontend/src/pages/settings/avatar-decoration.decoration.vue +++ b/packages/frontend/src/pages/settings/avatar-decoration.decoration.vue @@ -16,7 +16,9 @@ SPDX-License-Identifier: AGPL-3.0-only <script lang="ts" setup> import { } from 'vue'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; + +const $i = signinRequired(); const props = defineProps<{ active?: boolean; diff --git a/packages/frontend/src/pages/settings/avatar-decoration.dialog.vue b/packages/frontend/src/pages/settings/avatar-decoration.dialog.vue index 329ab4d47a..4cd0dd10e6 100644 --- a/packages/frontend/src/pages/settings/avatar-decoration.dialog.vue +++ b/packages/frontend/src/pages/settings/avatar-decoration.dialog.vue @@ -51,7 +51,9 @@ import MkModalWindow from '@/components/MkModalWindow.vue'; import MkSwitch from '@/components/MkSwitch.vue'; import { i18n } from '@/i18n.js'; import MkRange from '@/components/MkRange.vue'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; + +const $i = signinRequired(); const props = defineProps<{ usingIndex: number | null; diff --git a/packages/frontend/src/pages/settings/avatar-decoration.vue b/packages/frontend/src/pages/settings/avatar-decoration.vue index 6551fc917e..eb25f25ec8 100644 --- a/packages/frontend/src/pages/settings/avatar-decoration.vue +++ b/packages/frontend/src/pages/settings/avatar-decoration.vue @@ -51,10 +51,12 @@ import XDecoration from './avatar-decoration.decoration.vue'; import MkButton from '@/components/MkButton.vue'; import * as os from '@/os.js'; import { i18n } from '@/i18n.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import MkInfo from '@/components/MkInfo.vue'; import { definePageMetadata } from '@/scripts/page-metadata.js'; +const $i = signinRequired(); + const loading = ref(true); const avatarDecorations = ref<Misskey.entities.GetAvatarDecorationsResponse>([]); diff --git a/packages/frontend/src/pages/settings/drive.vue b/packages/frontend/src/pages/settings/drive.vue index 7857cf7125..e3a7b8ca80 100644 --- a/packages/frontend/src/pages/settings/drive.vue +++ b/packages/frontend/src/pages/settings/drive.vue @@ -71,7 +71,9 @@ import { defaultStore } from '@/store.js'; import MkChart from '@/components/MkChart.vue'; import { i18n } from '@/i18n.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; + +const $i = signinRequired(); const fetching = ref(true); const usage = ref<number | null>(null); diff --git a/packages/frontend/src/pages/settings/email.vue b/packages/frontend/src/pages/settings/email.vue index 309e025ada..015152c50a 100644 --- a/packages/frontend/src/pages/settings/email.vue +++ b/packages/frontend/src/pages/settings/email.vue @@ -54,12 +54,14 @@ import MkInfo from '@/components/MkInfo.vue'; import MkInput from '@/components/MkInput.vue'; import MkSwitch from '@/components/MkSwitch.vue'; import * as os from '@/os.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { i18n } from '@/i18n.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; import { instance } from '@/instance.js'; -const emailAddress = ref($i!.email); +const $i = signinRequired(); + +const emailAddress = ref($i.email); const onChangeReceiveAnnouncementEmail = (v) => { os.api('i/update', { @@ -78,11 +80,11 @@ async function saveEmailAddress() { }); } -const emailNotification_mention = ref($i!.emailNotificationTypes.includes('mention')); -const emailNotification_reply = ref($i!.emailNotificationTypes.includes('reply')); -const emailNotification_quote = ref($i!.emailNotificationTypes.includes('quote')); -const emailNotification_follow = ref($i!.emailNotificationTypes.includes('follow')); -const emailNotification_receiveFollowRequest = ref($i!.emailNotificationTypes.includes('receiveFollowRequest')); +const emailNotification_mention = ref($i.emailNotificationTypes.includes('mention')); +const emailNotification_reply = ref($i.emailNotificationTypes.includes('reply')); +const emailNotification_quote = ref($i.emailNotificationTypes.includes('quote')); +const emailNotification_follow = ref($i.emailNotificationTypes.includes('follow')); +const emailNotification_receiveFollowRequest = ref($i.emailNotificationTypes.includes('receiveFollowRequest')); const saveNotificationSettings = () => { os.api('i/update', { diff --git a/packages/frontend/src/pages/settings/import-export.vue b/packages/frontend/src/pages/settings/import-export.vue index 858983a214..d2dc3ea8bd 100644 --- a/packages/frontend/src/pages/settings/import-export.vue +++ b/packages/frontend/src/pages/settings/import-export.vue @@ -121,7 +121,7 @@ import { selectFile } from '@/scripts/select-file.js'; import { i18n } from '@/i18n.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; import { $i } from '@/account.js'; -import { defaultStore } from "@/store.js"; +import { defaultStore } from '@/store.js'; const excludeMutingUsers = ref(false); const excludeInactiveUsers = ref(false); diff --git a/packages/frontend/src/pages/settings/migration.vue b/packages/frontend/src/pages/settings/migration.vue index 15bf4691b2..d4c51a7c80 100644 --- a/packages/frontend/src/pages/settings/migration.vue +++ b/packages/frontend/src/pages/settings/migration.vue @@ -27,7 +27,7 @@ SPDX-License-Identifier: AGPL-3.0-only </div> </MkFolder> - <MkFolder :defaultOpen="!!$i?.movedTo"> + <MkFolder :defaultOpen="!!$i.movedTo"> <template #icon><i class="ti ti-plane-departure"></i></template> <template #label>{{ i18n.ts._accountMigration.moveTo }}</template> @@ -68,21 +68,23 @@ import MkUserInfo from '@/components/MkUserInfo.vue'; import * as os from '@/os.js'; import { i18n } from '@/i18n.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { unisonReload } from '@/scripts/unison-reload.js'; +const $i = signinRequired(); + const moveToAccount = ref(''); const movedTo = ref<Misskey.entities.UserDetailed>(); const accountAliases = ref(['']); async function init() { - if ($i?.movedTo) { + if ($i.movedTo) { movedTo.value = await os.api('users/show', { userId: $i.movedTo }); } else { moveToAccount.value = ''; } - if ($i?.alsoKnownAs && $i.alsoKnownAs.length > 0) { + if ($i.alsoKnownAs && $i.alsoKnownAs.length > 0) { const alsoKnownAs = await os.api('users/show', { userIds: $i.alsoKnownAs }); accountAliases.value = (alsoKnownAs && alsoKnownAs.length > 0) ? alsoKnownAs.map(user => `@${Misskey.acct.toString(user)}`) : ['']; } else { diff --git a/packages/frontend/src/pages/settings/mute-block.instance-mute.vue b/packages/frontend/src/pages/settings/mute-block.instance-mute.vue index 4b5080ea8f..8dc3e1acb4 100644 --- a/packages/frontend/src/pages/settings/mute-block.instance-mute.vue +++ b/packages/frontend/src/pages/settings/mute-block.instance-mute.vue @@ -20,10 +20,12 @@ import MkTextarea from '@/components/MkTextarea.vue'; import MkInfo from '@/components/MkInfo.vue'; import MkButton from '@/components/MkButton.vue'; import * as os from '@/os.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { i18n } from '@/i18n.js'; -const instanceMutes = ref($i!.mutedInstances.join('\n')); +const $i = signinRequired(); + +const instanceMutes = ref($i.mutedInstances.join('\n')); const changed = ref(false); async function save() { diff --git a/packages/frontend/src/pages/settings/mute-block.vue b/packages/frontend/src/pages/settings/mute-block.vue index 83f7baf428..dfb72a87dd 100644 --- a/packages/frontend/src/pages/settings/mute-block.vue +++ b/packages/frontend/src/pages/settings/mute-block.vue @@ -9,14 +9,14 @@ SPDX-License-Identifier: AGPL-3.0-only <template #icon><i class="ti ti-message-off"></i></template> <template #label>{{ i18n.ts.wordMute }}</template> - <XWordMute :muted="$i!.mutedWords" @save="saveMutedWords"/> + <XWordMute :muted="$i.mutedWords" @save="saveMutedWords"/> </MkFolder> <MkFolder> <template #icon><i class="ti ti-message-off"></i></template> <template #label>{{ i18n.ts.hardWordMute }}</template> - <XWordMute :muted="$i!.hardMutedWords" @save="saveHardMutedWords"/> + <XWordMute :muted="$i.hardMutedWords" @save="saveHardMutedWords"/> </MkFolder> <MkFolder> @@ -136,9 +136,11 @@ import { definePageMetadata } from '@/scripts/page-metadata.js'; import MkUserCardMini from '@/components/MkUserCardMini.vue'; import * as os from '@/os.js'; import { infoImageUrl } from '@/instance.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import MkFolder from '@/components/MkFolder.vue'; +const $i = signinRequired(); + const renoteMutingPagination = { endpoint: 'renote-mute/list' as const, limit: 10, diff --git a/packages/frontend/src/pages/settings/notifications.vue b/packages/frontend/src/pages/settings/notifications.vue index 98b82f7116..1e9515e588 100644 --- a/packages/frontend/src/pages/settings/notifications.vue +++ b/packages/frontend/src/pages/settings/notifications.vue @@ -62,12 +62,14 @@ import FormSection from '@/components/form/section.vue'; import MkFolder from '@/components/MkFolder.vue'; import MkSwitch from '@/components/MkSwitch.vue'; import * as os from '@/os.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { i18n } from '@/i18n.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; import MkPushNotificationAllowButton from '@/components/MkPushNotificationAllowButton.vue'; import { notificationTypes } from '@/const.js'; +const $i = signinRequired(); + const nonConfigurableNotificationTypes = ['note', 'roleAssigned', 'followRequestAccepted', 'achievementEarned']; const allowButton = shallowRef<InstanceType<typeof MkPushNotificationAllowButton>>(); @@ -86,11 +88,11 @@ async function readAllNotifications() { async function updateReceiveConfig(type, value) { await os.apiWithDialog('i/update', { notificationRecieveConfig: { - ...$i!.notificationRecieveConfig, + ...$i.notificationRecieveConfig, [type]: value, }, }).then(i => { - $i!.notificationRecieveConfig = i.notificationRecieveConfig; + $i.notificationRecieveConfig = i.notificationRecieveConfig; }); } diff --git a/packages/frontend/src/pages/settings/other.vue b/packages/frontend/src/pages/settings/other.vue index 340a9550b4..f6f0b8daa4 100644 --- a/packages/frontend/src/pages/settings/other.vue +++ b/packages/frontend/src/pages/settings/other.vue @@ -94,25 +94,19 @@ import MkKeyValue from '@/components/MkKeyValue.vue'; import MkButton from '@/components/MkButton.vue'; import * as os from '@/os.js'; import { defaultStore } from '@/store.js'; -import { signout, $i } from '@/account.js'; +import { signout, signinRequired } from '@/account.js'; import { i18n } from '@/i18n.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; import { unisonReload } from '@/scripts/unison-reload.js'; import FormSection from '@/components/form/section.vue'; +const $i = signinRequired(); + const reportError = computed(defaultStore.makeGetterSetter('reportError')); const enableCondensedLineForAcct = computed(defaultStore.makeGetterSetter('enableCondensedLineForAcct')); const devMode = computed(defaultStore.makeGetterSetter('devMode')); const defaultWithReplies = computed(defaultStore.makeGetterSetter('defaultWithReplies')); -function onChangeInjectFeaturedNote(v) { - os.api('i/update', { - injectFeaturedNote: v, - }).then((i) => { - $i!.injectFeaturedNote = i.injectFeaturedNote; - }); -} - async function deleteAccount() { { const { canceled } = await os.confirm({ diff --git a/packages/frontend/src/pages/settings/privacy.vue b/packages/frontend/src/pages/settings/privacy.vue index 67a2f2cb40..4f5bc847ac 100644 --- a/packages/frontend/src/pages/settings/privacy.vue +++ b/packages/frontend/src/pages/settings/privacy.vue @@ -80,9 +80,11 @@ import MkFolder from '@/components/MkFolder.vue'; import * as os from '@/os.js'; import { defaultStore } from '@/store.js'; import { i18n } from '@/i18n.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; +const $i = signinRequired(); + const isLocked = ref($i.isLocked); const autoAcceptFollowed = ref($i.autoAcceptFollowed); const noCrawle = ref($i.noCrawle); @@ -90,8 +92,8 @@ const preventAiLearning = ref($i.preventAiLearning); const isExplorable = ref($i.isExplorable); const hideOnlineStatus = ref($i.hideOnlineStatus); const publicReactions = ref($i.publicReactions); -const followingVisibility = ref($i?.followingVisibility); -const followersVisibility = ref($i?.followersVisibility); +const followingVisibility = ref($i.followingVisibility); +const followersVisibility = ref($i.followersVisibility); const defaultNoteVisibility = computed(defaultStore.makeGetterSetter('defaultNoteVisibility')); const defaultNoteLocalOnly = computed(defaultStore.makeGetterSetter('defaultNoteLocalOnly')); diff --git a/packages/frontend/src/pages/settings/profile.vue b/packages/frontend/src/pages/settings/profile.vue index d28c8284cf..57d84b9619 100644 --- a/packages/frontend/src/pages/settings/profile.vue +++ b/packages/frontend/src/pages/settings/profile.vue @@ -120,7 +120,7 @@ import FormSlot from '@/components/form/slot.vue'; import { selectFile } from '@/scripts/select-file.js'; import * as os from '@/os.js'; import { i18n } from '@/i18n.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { langmap } from '@/scripts/langmap.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; import { claimAchievement } from '@/scripts/achievements.js'; @@ -128,6 +128,8 @@ import { defaultStore } from '@/store.js'; import MkInfo from '@/components/MkInfo.vue'; import MkTextarea from '@/components/MkTextarea.vue'; +const $i = signinRequired(); + const Sortable = defineAsyncComponent(() => import('vuedraggable').then(x => x.default)); const reactionAcceptance = computed(defaultStore.makeGetterSetter('reactionAcceptance')); @@ -148,7 +150,7 @@ watch(() => profile, () => { deep: true, }); -const fields = ref($i?.fields.map(field => ({ id: Math.random().toString(), name: field.name, value: field.value })) ?? []); +const fields = ref($i.fields.map(field => ({ id: Math.random().toString(), name: field.name, value: field.value })) ?? []); const fieldEditMode = ref(false); function addField() { diff --git a/packages/frontend/src/pages/settings/roles.vue b/packages/frontend/src/pages/settings/roles.vue index 40671f7132..bb37730e35 100644 --- a/packages/frontend/src/pages/settings/roles.vue +++ b/packages/frontend/src/pages/settings/roles.vue @@ -27,15 +27,11 @@ import { computed } from 'vue'; import FormSection from '@/components/form/section.vue'; import * as os from '@/os.js'; import { i18n } from '@/i18n.js'; -import { $i } from '@/account.js'; +import { signinRequired } from '@/account.js'; import { definePageMetadata } from '@/scripts/page-metadata.js'; import MkRolePreview from '@/components/MkRolePreview.vue'; -function save() { - os.apiWithDialog('i/update', { - - }); -} +const $i = signinRequired(); const headerActions = computed(() => []);