diff --git a/biome.json b/biome.json index d64639d52..6a464a0e5 100644 --- a/biome.json +++ b/biome.json @@ -132,7 +132,11 @@ "groups": [ [":NODE:", ":PACKAGE:", "!src/**", "!@fortawesome/**"], ":BLANK_LINE:", - [":PATH:", "src/**"], + [":PATH:", "src/components/**"], + ":BLANK_LINE:", + [":PATH:", "src/stores/**"], + ":BLANK_LINE:", + [":PATH:", "src/**", "src/stores/**", "src/components/**"], ":BLANK_LINE:", "@fortawesome/fontawesome-svg-core", "@fortawesome/*" diff --git a/changelog.d/instance-store-migration.skip b/changelog.d/instance-store-migration.skip new file mode 100644 index 000000000..e69de29bb diff --git a/package.json b/package.json index bdd1acfbe..20c01a0b3 100644 --- a/package.json +++ b/package.json @@ -63,6 +63,7 @@ "@babel/preset-env": "7.28.5", "@babel/register": "7.28.3", "@biomejs/biome": "2.3.11", + "@pinia/testing": "1.0.3", "@ungap/event-target": "0.2.4", "@vitejs/plugin-vue": "^5.2.1", "@vitejs/plugin-vue-jsx": "^4.1.1", diff --git a/src/App.js b/src/App.js index 33645c63d..0714ced1d 100644 --- a/src/App.js +++ b/src/App.js @@ -1,4 +1,5 @@ import { throttle } from 'lodash' +import { mapState } from 'pinia' import { defineAsyncComponent } from 'vue' import { mapGetters } from 'vuex' @@ -20,8 +21,11 @@ import UserReportingModal from './components/user_reporting_modal/user_reporting import WhoToFollowPanel from './components/who_to_follow_panel/who_to_follow_panel.vue' import { getOrCreateServiceWorker } from './services/sw/sw' import { windowHeight, windowWidth } from './services/window_utils/window_utils' -import { useInterfaceStore } from './stores/interface' -import { useShoutStore } from './stores/shout' + +import { useInstanceStore } from 'src/stores/instance.js' +import { useInstanceCapabilitiesStore } from 'src/stores/instance_capabilities.js' +import { useInterfaceStore } from 'src/stores/interface.js' +import { useShoutStore } from 'src/stores/shout.js' export default { name: 'app', @@ -80,7 +84,7 @@ export default { window.addEventListener('resize', this.updateMobileState) this.scrollParent.addEventListener('scroll', this.updateScrollState) - if (useInterfaceStore().themeApplied) { + if (this.themeApplied) { this.setThemeBodyClass() this.removeSplash() } @@ -91,12 +95,9 @@ export default { this.scrollParent.removeEventListener('scroll', this.updateScrollState) }, computed: { - themeApplied() { - return useInterfaceStore().themeApplied - }, currentTheme() { - if (useInterfaceStore().styleDataUsed) { - const styleMeta = useInterfaceStore().styleDataUsed.find( + if (this.styleDataUsed) { + const styleMeta = this.styleDataUsed.find( (x) => x.component === '@meta', ) @@ -134,9 +135,7 @@ export default { return this.currentUser.background_image }, instanceBackground() { - return this.mergedConfig.hideInstanceWallpaper - ? null - : this.$store.state.instance.background + return this.mergedConfig.hideInstanceWallpaper ? null : this.background }, background() { return this.userBackground || this.instanceBackground @@ -151,16 +150,6 @@ export default { shout() { return useShoutStore().joined }, - suggestionsEnabled() { - return this.$store.state.instance.suggestionsEnabled - }, - showInstanceSpecificPanel() { - return ( - this.$store.state.instance.showInstanceSpecificPanel && - !this.$store.getters.mergedConfig.hideISP && - this.$store.state.instance.instanceSpecificPanelContent - ) - }, isChats() { return this.$route.name === 'chat' || this.$route.name === 'chats' }, @@ -175,24 +164,12 @@ export default { this.layoutType === 'mobile' ) }, - showFeaturesPanel() { - return this.$store.state.instance.showFeaturesPanel - }, - editingAvailable() { - return this.$store.state.instance.editingAvailable - }, shoutboxPosition() { return this.$store.getters.mergedConfig.alwaysShowNewPostButton || false }, hideShoutbox() { return this.$store.getters.mergedConfig.hideShoutbox }, - layoutType() { - return useInterfaceStore().layoutType - }, - privateMode() { - return this.$store.state.instance.private - }, reverseLayout() { const { thirdColumnMode, sidebarRight: reverseSetting } = this.$store.getters.mergedConfig @@ -213,7 +190,30 @@ export default { scrollParent() { return window /* this.$refs.appContentRef */ }, + showInstanceSpecificPanel() { + return ( + this.instanceSpecificPanelPresent && + !this.$store.getters.mergedConfig.hideISP + ) + }, ...mapGetters(['mergedConfig']), + ...mapState(useInterfaceStore, [ + 'themeApplied', + 'styleDataUsed', + 'layoutType', + ]), + ...mapState(useInstanceStore, ['styleDataUsed']), + ...mapState(useInstanceCapabilitiesStore, [ + 'suggestionsEnabled', + 'editingAvailable', + ]), + ...mapState(useInstanceStore, { + background: (store) => store.instanceIdentity.background, + showFeaturesPanel: (store) => store.instanceIdentity.showFeaturesPanel, + instanceSpecificPanelPresent: (store) => + store.instanceIdentity.showInstanceSpecificPanel && + store.instanceIdentity.instanceSpecificPanelContent, + }), }, methods: { resizeHandler() { diff --git a/src/boot/after_store.js b/src/boot/after_store.js index 1a2be5bd7..b7e97cf45 100644 --- a/src/boot/after_store.js +++ b/src/boot/after_store.js @@ -14,16 +14,6 @@ import { config.autoAddCss = false -import VBodyScrollLock from 'src/directives/body_scroll_lock' -import { - instanceDefaultConfig, - staticOrApiConfigDefault, -} from 'src/modules/default_config_state.js' -import { useAnnouncementsStore } from 'src/stores/announcements' -import { useAuthFlowStore } from 'src/stores/auth_flow' -import { useI18nStore } from 'src/stores/i18n' -import { useInterfaceStore } from 'src/stores/interface' -import { useOAuthStore } from 'src/stores/oauth' import App from '../App.vue' import backendInteractorService from '../services/backend_interactor_service/backend_interactor_service.js' import FaviconService from '../services/favicon_service/favicon_service.js' @@ -35,6 +25,21 @@ import { } from '../services/window_utils/window_utils' import routes from './routes' +import { useAnnouncementsStore } from 'src/stores/announcements' +import { useAuthFlowStore } from 'src/stores/auth_flow' +import { useEmojiStore } from 'src/stores/emoji.js' +import { useI18nStore } from 'src/stores/i18n' +import { useInstanceStore } from 'src/stores/instance.js' +import { useInstanceCapabilitiesStore } from 'src/stores/instance_capabilities.js' +import { useInterfaceStore } from 'src/stores/interface.js' +import { useOAuthStore } from 'src/stores/oauth' + +import VBodyScrollLock from 'src/directives/body_scroll_lock' +import { + instanceDefaultConfig, + staticOrApiConfigDefault, +} from 'src/modules/default_config_state.js' + let staticInitialResults = null const parsedInitialResults = () => { @@ -78,29 +83,29 @@ const getInstanceConfig = async ({ store }) => { const textlimit = data.max_toot_chars const vapidPublicKey = data.pleroma.vapid_public_key - store.dispatch('setInstanceOption', { - name: 'pleromaExtensionsAvailable', - value: data.pleroma, - }) - store.dispatch('setInstanceOption', { + useInstanceCapabilitiesStore().set( + 'pleromaExtensionsAvailable', + data.pleroma, + ) + useInstanceStore().set({ name: 'textlimit', value: textlimit, }) - store.dispatch('setInstanceOption', { + useInstanceStore().set({ name: 'accountApprovalRequired', value: data.approval_required, }) - store.dispatch('setInstanceOption', { + useInstanceStore().set({ name: 'birthdayRequired', value: !!data.pleroma?.metadata.birthday_required, }) - store.dispatch('setInstanceOption', { + useInstanceStore().set({ name: 'birthdayMinAge', value: data.pleroma?.metadata.birthday_min_age || 0, }) if (vapidPublicKey) { - store.dispatch('setInstanceOption', { + useInstanceStore().set({ name: 'vapidPublicKey', value: vapidPublicKey, }) @@ -161,14 +166,18 @@ const setSettings = async ({ apiConfig, staticConfig, store }) => { config = Object.assign({}, staticConfig, apiConfig) } - const copyInstanceOption = (name) => { - if (typeof config[name] !== 'undefined') { - store.dispatch('setInstanceOption', { name, value: config[name] }) + const copyInstanceOption = ({ source, destination }) => { + if (typeof config[source] !== 'undefined') { + useInstanceStore().set({ path: destination, value: config[source] }) } } - Object.keys(staticOrApiConfigDefault).forEach(copyInstanceOption) - Object.keys(instanceDefaultConfig).forEach(copyInstanceOption) + Object.keys(staticOrApiConfigDefault) + .map((k) => ({ source: k, destination: `instanceIdentity.${k}` })) + .forEach(copyInstanceOption) + Object.keys(instanceDefaultConfig) + .map((k) => ({ source: k, destination: `prefsStorage.${k}` })) + .forEach(copyInstanceOption) useAuthFlowStore().setInitialStrategy(config.loginMethod) } @@ -178,7 +187,7 @@ const getTOS = async ({ store }) => { const res = await window.fetch('/static/terms-of-service.html') if (res.ok) { const html = await res.text() - store.dispatch('setInstanceOption', { name: 'tos', value: html }) + useInstanceStore().set({ name: 'instanceIdentity.tos', value: html }) } else { throw res } @@ -192,8 +201,8 @@ const getInstancePanel = async ({ store }) => { const res = await preloadFetch('/instance/panel.html') if (res.ok) { const html = await res.text() - store.dispatch('setInstanceOption', { - name: 'instanceSpecificPanelContent', + useInstanceStore().set({ + path: 'instanceIdentity.instanceSpecificPanelContent', value: html, }) } else { @@ -227,7 +236,7 @@ const getStickers = async ({ store }) => { ).sort((a, b) => { return a.meta.title.localeCompare(b.meta.title) }) - store.dispatch('setInstanceOption', { name: 'stickers', value: stickers }) + useEmojiStore().setStickers(stickers) } else { throw res } @@ -248,7 +257,7 @@ const getAppSecret = async ({ store }) => { const resolveStaffAccounts = ({ store, accounts }) => { const nicknames = accounts.map((uri) => uri.split('/').pop()) - store.dispatch('setInstanceOption', { + useInstanceStore().set({ name: 'staffAccounts', value: nicknames, }) @@ -262,160 +271,158 @@ const getNodeInfo = async ({ store }) => { const data = await res.json() const metadata = data.metadata const features = metadata.features - store.dispatch('setInstanceOption', { - name: 'name', + useInstanceStore().set({ + path: 'name', value: metadata.nodeName, }) - store.dispatch('setInstanceOption', { - name: 'registrationOpen', + useInstanceStore().set({ + path: 'registrationOpen', value: data.openRegistrations, }) - store.dispatch('setInstanceOption', { - name: 'mediaProxyAvailable', - value: features.includes('media_proxy'), - }) - store.dispatch('setInstanceOption', { - name: 'safeDM', - value: features.includes('safe_dm_mentions'), - }) - store.dispatch('setInstanceOption', { - name: 'shoutAvailable', - value: features.includes('chat'), - }) - store.dispatch('setInstanceOption', { - name: 'pleromaChatMessagesAvailable', - value: features.includes('pleroma_chat_messages'), - }) - store.dispatch('setInstanceOption', { - name: 'pleromaCustomEmojiReactionsAvailable', - value: - features.includes('pleroma_custom_emoji_reactions') || + useInstanceCapabilitiesStore().set( + 'mediaProxyAvailable', + features.includes('media_proxy'), + ) + useInstanceCapabilitiesStore().set( + 'safeDM', + features.includes('safe_dm_mentions'), + ) + useInstanceCapabilitiesStore().set( + 'shoutAvailable', + features.includes('chat'), + ) + useInstanceCapabilitiesStore().set( + 'pleromaChatMessagesAvailable', + features.includes('pleroma_chat_messages'), + ) + useInstanceCapabilitiesStore().set( + 'pleromaCustomEmojiReactionsAvailable', + + features.includes('pleroma_custom_emoji_reactions') || features.includes('custom_emoji_reactions'), - }) - store.dispatch('setInstanceOption', { - name: 'pleromaBookmarkFoldersAvailable', - value: features.includes('pleroma:bookmark_folders'), - }) - store.dispatch('setInstanceOption', { - name: 'gopherAvailable', - value: features.includes('gopher'), - }) - store.dispatch('setInstanceOption', { - name: 'pollsAvailable', - value: features.includes('polls'), - }) - store.dispatch('setInstanceOption', { - name: 'editingAvailable', - value: features.includes('editing'), - }) - store.dispatch('setInstanceOption', { - name: 'pollLimits', - value: metadata.pollLimits, - }) - store.dispatch('setInstanceOption', { - name: 'mailerEnabled', - value: metadata.mailerEnabled, - }) - store.dispatch('setInstanceOption', { - name: 'quotingAvailable', - value: features.includes('quote_posting'), - }) - store.dispatch('setInstanceOption', { - name: 'groupActorAvailable', - value: features.includes('pleroma:group_actors'), - }) - store.dispatch('setInstanceOption', { - name: 'blockExpiration', - value: features.includes('pleroma:block_expiration'), - }) - store.dispatch('setInstanceOption', { - name: 'localBubbleInstances', + ) + useInstanceCapabilitiesStore().set( + 'pleromaBookmarkFoldersAvailable', + features.includes('pleroma:bookmark_folders'), + ) + useInstanceCapabilitiesStore().set( + 'gopherAvailable', + features.includes('gopher'), + ) + useInstanceCapabilitiesStore().set( + 'pollsAvailable', + features.includes('polls'), + ) + useInstanceCapabilitiesStore().set( + 'editingAvailable', + features.includes('editing'), + ) + useInstanceCapabilitiesStore().set( + 'mailerEnabled', + metadata.mailerEnabled, + ) + useInstanceCapabilitiesStore().set( + 'quotingAvailable', + features.includes('quote_posting'), + ) + useInstanceCapabilitiesStore().set( + 'groupActorAvailable', + features.includes('pleroma:group_actors'), + ) + useInstanceCapabilitiesStore().set( + 'blockExpiration', + features.includes('pleroma:block_expiration'), + ) + useInstanceStore().set({ + path: 'localBubbleInstances', value: metadata.localBubbleInstances ?? [], }) + useInstanceCapabilitiesStore().set( + 'localBubble', + (metadata.localBubbleInstances ?? []).length > 0, + ) + useInstanceStore().set({ + path: 'limits.pollLimits', + value: metadata.pollLimits, + }) const uploadLimits = metadata.uploadLimits - store.dispatch('setInstanceOption', { - name: 'uploadlimit', + useInstanceStore().set({ + path: 'limits.uploadlimit', value: parseInt(uploadLimits.general), }) - store.dispatch('setInstanceOption', { - name: 'avatarlimit', + useInstanceStore().set({ + path: 'limits.avatarlimit', value: parseInt(uploadLimits.avatar), }) - store.dispatch('setInstanceOption', { - name: 'backgroundlimit', + useInstanceStore().set({ + path: 'limits.backgroundlimit', value: parseInt(uploadLimits.background), }) - store.dispatch('setInstanceOption', { - name: 'bannerlimit', + useInstanceStore().set({ + path: 'limits.bannerlimit', value: parseInt(uploadLimits.banner), }) - store.dispatch('setInstanceOption', { - name: 'fieldsLimits', + useInstanceStore().set({ + path: 'limits.fieldsLimits', value: metadata.fieldsLimits, }) - store.dispatch('setInstanceOption', { - name: 'restrictedNicknames', + useInstanceStore().set({ + path: 'restrictedNicknames', value: metadata.restrictedNicknames, }) - store.dispatch('setInstanceOption', { - name: 'postFormats', - value: metadata.postFormats, - }) + useInstanceCapabilitiesStore().set('postFormats', metadata.postFormats) const suggestions = metadata.suggestions - store.dispatch('setInstanceOption', { - name: 'suggestionsEnabled', - value: suggestions.enabled, - }) - store.dispatch('setInstanceOption', { - name: 'suggestionsWeb', - value: suggestions.web, - }) + useInstanceCapabilitiesStore().set( + 'suggestionsEnabled', + suggestions.enabled, + ) + // this is unused, why? + useInstanceCapabilitiesStore().set('suggestionsWeb', suggestions.web) const software = data.software - store.dispatch('setInstanceOption', { + useInstanceStore().set({ name: 'backendVersion', value: software.version, }) - store.dispatch('setInstanceOption', { + useInstanceStore().set({ name: 'backendRepository', value: software.repository, }) const priv = metadata.private - store.dispatch('setInstanceOption', { name: 'private', value: priv }) + useInstanceStore().set({ name: 'privateMode', value: priv }) const frontendVersion = window.___pleromafe_commit_hash - store.dispatch('setInstanceOption', { + useInstanceStore().set({ name: 'frontendVersion', value: frontendVersion, }) const federation = metadata.federation - store.dispatch('setInstanceOption', { - name: 'tagPolicyAvailable', - value: - typeof federation.mrf_policies === 'undefined' - ? false - : metadata.federation.mrf_policies.includes('TagPolicy'), - }) + useInstanceCapabilitiesStore().set( + 'tagPolicyAvailable', + typeof federation.mrf_policies === 'undefined' + ? false + : metadata.federation.mrf_policies.includes('TagPolicy'), + ) - store.dispatch('setInstanceOption', { - name: 'federationPolicy', + useInstanceStore().set({ + path: 'federationPolicy', value: federation, }) - store.dispatch('setInstanceOption', { - name: 'federating', + useInstanceStore().set({ + path: 'federating', value: typeof federation.enabled === 'undefined' ? true : federation.enabled, }) const accountActivationRequired = metadata.accountActivationRequired - store.dispatch('setInstanceOption', { - name: 'accountActivationRequired', + useInstanceStore().set({ + path: 'accountActivationRequired', value: accountActivationRequired, }) @@ -526,7 +533,7 @@ const afterStoreSetup = async ({ pinia, store, storageError, i18n }) => { typeof overrides.target !== 'undefined' ? overrides.target : window.location.origin - store.dispatch('setInstanceOption', { name: 'server', value: server }) + useInstanceStore().set({ name: 'server', value: server }) await setConfig({ store }) try { diff --git a/src/boot/routes.js b/src/boot/routes.js index 3296755a1..193daf4a7 100644 --- a/src/boot/routes.js +++ b/src/boot/routes.js @@ -32,12 +32,17 @@ import BookmarkFolderEdit from '../components/bookmark_folder_edit/bookmark_fold import BookmarkFolders from '../components/bookmark_folders/bookmark_folders.vue' import QuotesTimeline from '../components/quotes_timeline/quotes_timeline.vue' +import { useInstanceStore } from 'src/stores/instance.js' +import { useInstanceCapabilitiesStore } from 'src/stores/instance_capabilities.js' + export default (store) => { const validateAuthenticatedRoute = (to, from, next) => { if (store.state.users.currentUser) { next() } else { - next(store.state.instance.redirectRootNoLogin || '/main/all') + next( + useInstanceStore().instanceIdentity.redirectRootNoLogin || '/main/all', + ) } } @@ -48,8 +53,9 @@ export default (store) => { redirect: () => { return ( (store.state.users.currentUser - ? store.state.instance.redirectRootLogin - : store.state.instance.redirectRootNoLogin) || '/main/all' + ? useInstanceStore().instanceIdentity.redirectRootLogin + : useInstanceStore().instanceIdentity.redirectRootNoLogin) || + '/main/all' ) }, }, @@ -200,7 +206,7 @@ export default (store) => { }, ] - if (store.state.instance.pleromaChatMessagesAvailable) { + if (useInstanceCapabilitiesStore().pleromaChatMessagesAvailable) { routes = routes.concat([ { name: 'chat', diff --git a/src/components/about/about.js b/src/components/about/about.js index d091dfd0a..f52d5c797 100644 --- a/src/components/about/about.js +++ b/src/components/about/about.js @@ -4,6 +4,8 @@ import MRFTransparencyPanel from '../mrf_transparency_panel/mrf_transparency_pan import StaffPanel from '../staff_panel/staff_panel.vue' import TermsOfServicePanel from '../terms_of_service_panel/terms_of_service_panel.vue' +import { useInstanceStore } from 'src/stores/instance.js' + const About = { components: { InstanceSpecificPanel, @@ -14,13 +16,13 @@ const About = { }, computed: { showFeaturesPanel() { - return this.$store.state.instance.showFeaturesPanel + return useInstanceStore().instanceIdentity.showFeaturesPanel }, showInstanceSpecificPanel() { return ( - this.$store.state.instance.showInstanceSpecificPanel && + useInstanceStore().instanceIdentity.showInstanceSpecificPanel && !this.$store.getters.mergedConfig.hideISP && - this.$store.state.instance.instanceSpecificPanelContent + useInstanceStore().instanceIdentity.instanceSpecificPanelContent ) }, }, diff --git a/src/components/account_actions/account_actions.js b/src/components/account_actions/account_actions.js index ee94dc544..8fce4b5af 100644 --- a/src/components/account_actions/account_actions.js +++ b/src/components/account_actions/account_actions.js @@ -1,12 +1,14 @@ -import { mapState } from 'vuex' +import { mapState } from 'pinia' import UserListMenu from 'src/components/user_list_menu/user_list_menu.vue' import UserTimedFilterModal from 'src/components/user_timed_filter_modal/user_timed_filter_modal.vue' -import { useReportsStore } from 'src/stores/reports' import ConfirmModal from '../confirm_modal/confirm_modal.vue' import Popover from '../popover/popover.vue' import ProgressButton from '../progress_button/progress_button.vue' +import { useInstanceCapabilitiesStore } from 'src/stores/instance_capabilities.js' +import { useReportsStore } from 'src/stores/reports' + import { library } from '@fortawesome/fontawesome-svg-core' import { faEllipsisV } from '@fortawesome/free-solid-svg-icons' @@ -92,11 +94,10 @@ const AccountActions = { shouldConfirmRemoveUserFromFollowers() { return this.$store.getters.mergedConfig.modalOnRemoveUserFromFollowers }, - ...mapState({ - blockExpirationSupported: (state) => state.instance.blockExpiration, - pleromaChatMessagesAvailable: (state) => - state.instance.pleromaChatMessagesAvailable, - }), + ...mapState(useInstanceCapabilitiesStore, [ + 'blockExpiration', + 'pleromaChatMessagesAvailable', + ]), }, } diff --git a/src/components/account_actions/account_actions.vue b/src/components/account_actions/account_actions.vue index cc00a735d..94cb91ee0 100644 --- a/src/components/account_actions/account_actions.vue +++ b/src/components/account_actions/account_actions.vue @@ -95,7 +95,7 @@ state.instance.blockExpiration, - }), + ...mapState(useInstanceCapabilitiesStore, ['blockExpiration']), }, components: { BasicUserCard, + UserTimedFilterModal, }, methods: { unblockUser() { this.$store.dispatch('unblockUser', this.user.id) }, blockUser() { - if (this.blockExpirationSupported) { + if (this.blockExpiration) { this.$refs.timedBlockDialog.optionallyPrompt() } else { this.$store.dispatch('blockUser', { id: this.user.id }) diff --git a/src/components/bookmark_folder_edit/bookmark_folder_edit.js b/src/components/bookmark_folder_edit/bookmark_folder_edit.js index a658a0f40..a036895bf 100644 --- a/src/components/bookmark_folder_edit/bookmark_folder_edit.js +++ b/src/components/bookmark_folder_edit/bookmark_folder_edit.js @@ -1,8 +1,9 @@ -import { useBookmarkFoldersStore } from 'src/stores/bookmark_folders' -import { useInterfaceStore } from 'src/stores/interface' import apiService from '../../services/api/api.service' import EmojiPicker from '../emoji_picker/emoji_picker.vue' +import { useBookmarkFoldersStore } from 'src/stores/bookmark_folders.js' +import { useInterfaceStore } from 'src/stores/interface.js' + const BookmarkFolderEdit = { data() { return { diff --git a/src/components/bookmark_folders/bookmark_folders.js b/src/components/bookmark_folders/bookmark_folders.js index 8e09abb31..1147fd3a5 100644 --- a/src/components/bookmark_folders/bookmark_folders.js +++ b/src/components/bookmark_folders/bookmark_folders.js @@ -1,6 +1,7 @@ -import { useBookmarkFoldersStore } from 'src/stores/bookmark_folders' import BookmarkFolderCard from '../bookmark_folder_card/bookmark_folder_card.vue' +import { useBookmarkFoldersStore } from 'src/stores/bookmark_folders.js' + const BookmarkFolders = { data() { return { diff --git a/src/components/bookmark_folders_menu/bookmark_folders_menu_content.js b/src/components/bookmark_folders_menu/bookmark_folders_menu_content.js index e84b3bc85..be1fb06ea 100644 --- a/src/components/bookmark_folders_menu/bookmark_folders_menu_content.js +++ b/src/components/bookmark_folders_menu/bookmark_folders_menu_content.js @@ -2,7 +2,8 @@ import { mapState } from 'pinia' import { getBookmarkFolderEntries } from 'src/components/navigation/filter.js' import NavigationEntry from 'src/components/navigation/navigation_entry.vue' -import { useBookmarkFoldersStore } from 'src/stores/bookmark_folders' + +import { useBookmarkFoldersStore } from 'src/stores/bookmark_folders.js' export const BookmarkFoldersMenuContent = { props: ['showPin'], diff --git a/src/components/chat/chat.js b/src/components/chat/chat.js index 6dd69ada4..caeb2aea7 100644 --- a/src/components/chat/chat.js +++ b/src/components/chat/chat.js @@ -2,7 +2,6 @@ import _ from 'lodash' import { mapState as mapPiniaState } from 'pinia' import { mapGetters, mapState } from 'vuex' -import { useInterfaceStore } from 'src/stores/interface.js' import { WSConnectionStatus } from '../../services/api/api.service.js' import chatService from '../../services/chat_service/chat_service.js' import { buildFakeMessage } from '../../services/chat_utils/chat_utils.js' @@ -17,6 +16,8 @@ import { isScrollable, } from './chat_layout_utils.js' +import { useInterfaceStore } from 'src/stores/interface.js' + import { library } from '@fortawesome/fontawesome-svg-core' import { faChevronDown, faChevronLeft } from '@fortawesome/free-solid-svg-icons' diff --git a/src/components/chat_list_item/chat_list_item.js b/src/components/chat_list_item/chat_list_item.js index 0923a8568..4f4ea4955 100644 --- a/src/components/chat_list_item/chat_list_item.js +++ b/src/components/chat_list_item/chat_list_item.js @@ -1,12 +1,13 @@ import { mapState } from 'vuex' -import fileType from 'src/services/file_type/file_type.service' import AvatarList from '../avatar_list/avatar_list.vue' import ChatTitle from '../chat_title/chat_title.vue' import StatusBody from '../status_content/status_content.vue' import Timeago from '../timeago/timeago.vue' import UserAvatar from '../user_avatar/user_avatar.vue' +import fileType from 'src/services/file_type/file_type.service' + const ChatListItem = { name: 'ChatListItem', props: ['chat'], diff --git a/src/components/chat_message/chat_message.js b/src/components/chat_message/chat_message.js index f3cc495c2..af3701ebf 100644 --- a/src/components/chat_message/chat_message.js +++ b/src/components/chat_message/chat_message.js @@ -2,7 +2,6 @@ import { mapState as mapPiniaState } from 'pinia' import { defineAsyncComponent } from 'vue' import { mapGetters, mapState } from 'vuex' -import { useInterfaceStore } from 'src/stores/interface' import Attachment from '../attachment/attachment.vue' import ChatMessageDate from '../chat_message_date/chat_message_date.vue' import Gallery from '../gallery/gallery.vue' @@ -11,6 +10,9 @@ import Popover from '../popover/popover.vue' import StatusContent from '../status_content/status_content.vue' import UserAvatar from '../user_avatar/user_avatar.vue' +import { useInstanceStore } from 'src/stores/instance.js' +import { useInterfaceStore } from 'src/stores/interface' + import { library } from '@fortawesome/fontawesome-svg-core' import { faEllipsisH, faTimes } from '@fortawesome/free-solid-svg-icons' @@ -74,7 +76,7 @@ const ChatMessage = { }), ...mapState({ currentUser: (state) => state.users.currentUser, - restrictedNicknames: (state) => state.instance.restrictedNicknames, + restrictedNicknames: (state) => useInstanceStore().restrictedNicknames, }), popoverMarginStyle() { if (this.isCurrentUser) { diff --git a/src/components/component_preview/component_preview.js b/src/components/component_preview/component_preview.js index 70696f56b..1d54f58de 100644 --- a/src/components/component_preview/component_preview.js +++ b/src/components/component_preview/component_preview.js @@ -1,5 +1,6 @@ import Checkbox from 'src/components/checkbox/checkbox.vue' import ColorInput from 'src/components/color_input/color_input.vue' + import genRandomSeed from 'src/services/random_seed/random_seed.service.js' import { adoptStyleSheets, diff --git a/src/components/conversation/conversation.js b/src/components/conversation/conversation.js index 3caf4add7..cb7cf4782 100644 --- a/src/components/conversation/conversation.js +++ b/src/components/conversation/conversation.js @@ -2,13 +2,14 @@ import { clone, filter, findIndex, get, reduce } from 'lodash' import { mapState as mapPiniaState } from 'pinia' import { mapGetters, mapState } from 'vuex' -import { useInterfaceStore } from 'src/stores/interface' import { WSConnectionStatus } from '../../services/api/api.service.js' import QuickFilterSettings from '../quick_filter_settings/quick_filter_settings.vue' import QuickViewSettings from '../quick_view_settings/quick_view_settings.vue' import Status from '../status/status.vue' import ThreadTree from '../thread_tree/thread_tree.vue' +import { useInterfaceStore } from 'src/stores/interface' + import { library } from '@fortawesome/fontawesome-svg-core' import { faAngleDoubleDown, diff --git a/src/components/desktop_nav/desktop_nav.js b/src/components/desktop_nav/desktop_nav.js index 8ab54b3df..943c66d1e 100644 --- a/src/components/desktop_nav/desktop_nav.js +++ b/src/components/desktop_nav/desktop_nav.js @@ -1,8 +1,11 @@ import SearchBar from 'components/search_bar/search_bar.vue' +import { mapActions, mapState } from 'pinia' -import { useInterfaceStore } from 'src/stores/interface' import ConfirmModal from '../confirm_modal/confirm_modal.vue' +import { useInstanceStore } from 'src/stores/instance.js' +import { useInterfaceStore } from 'src/stores/interface' + import { library } from '@fortawesome/fontawesome-svg-core' import { faBell, @@ -51,7 +54,7 @@ export default { }), computed: { enableMask() { - return this.supportsMask && this.$store.state.instance.logoMask + return this.supportsMask && this.logoMask }, logoStyle() { return { @@ -61,7 +64,7 @@ export default { logoMaskStyle() { return this.enableMask ? { - 'mask-image': `url(${this.$store.state.instance.logo})`, + 'mask-image': `url(${this.logo})`, } : { 'background-color': this.enableMask ? '' : 'transparent', @@ -70,7 +73,7 @@ export default { logoBgStyle() { return Object.assign( { - margin: `${this.$store.state.instance.logoMargin} 0`, + margin: `${this.logoMargin} 0`, opacity: this.searchBarHidden ? 1 : 0, }, this.enableMask @@ -80,24 +83,18 @@ export default { }, ) }, - logo() { - return this.$store.state.instance.logo - }, - sitename() { - return this.$store.state.instance.name - }, - hideSitename() { - return this.$store.state.instance.hideSitename - }, - logoLeft() { - return this.$store.state.instance.logoLeft - }, + ...mapState(useInstanceStore, ['privateMode']), + ...mapState(useInstanceStore, { + logoMask: (store) => store.instanceIdentity.logoMask, + logo: (store) => store.instanceIdentity.logo, + logoLeft: (store) => store.instanceIdentity.logoLeft, + logoMargin: (store) => store.instanceIdentity.logoMargin, + sitename: (store) => store.instanceIdentity.name, + hideSitename: (store) => store.instanceIdentity.hideSitename, + }), currentUser() { return this.$store.state.users.currentUser }, - privateMode() { - return this.$store.state.instance.private - }, shouldConfirmLogout() { return this.$store.getters.mergedConfig.modalOnLogout }, @@ -127,11 +124,6 @@ export default { onSearchBarToggled(hidden) { this.searchBarHidden = hidden }, - openSettingsModal() { - useInterfaceStore().openSettingsModal('user') - }, - openAdminModal() { - useInterfaceStore().openSettingsModal('admin') - }, + ...mapActions(useInterfaceStore, ['openSettingsModal']), }, } diff --git a/src/components/desktop_nav/desktop_nav.vue b/src/components/desktop_nav/desktop_nav.vue index 49382f8ee..da427f2a1 100644 --- a/src/components/desktop_nav/desktop_nav.vue +++ b/src/components/desktop_nav/desktop_nav.vue @@ -40,7 +40,7 @@