diff options
Diffstat (limited to 'src/client/store.ts')
| -rw-r--r-- | src/client/store.ts | 267 |
1 files changed, 20 insertions, 247 deletions
diff --git a/src/client/store.ts b/src/client/store.ts index 07566954a2..fd469a4be3 100644 --- a/src/client/store.ts +++ b/src/client/store.ts @@ -1,10 +1,7 @@ -import Vuex from 'vuex'; +import { createStore } from 'vuex'; import createPersistedState from 'vuex-persistedstate'; import * as nestedProperty from 'nested-property'; -import { faSatelliteDish, faTerminal, faHashtag, faBroadcastTower, faFireAlt, faSearch, faStar, faAt, faListUl, faUserClock, faUsers, faCloud, faGamepad, faFileAlt, faSatellite, faDoorClosed, faColumns } from '@fortawesome/free-solid-svg-icons'; -import { faBell, faEnvelope, faComments } from '@fortawesome/free-regular-svg-icons'; -import { AiScript, utils, values } from '@syuilo/aiscript'; -import { apiUrl, deckmode } from './config'; +import { api } from '@/os'; import { erase } from '../prelude/array'; export const defaultSettings = { @@ -72,10 +69,10 @@ export const defaultDeviceSettings = { animation: true, animatedMfm: true, imageNewTab: false, + chatOpenBehavior: 'page', showFixedPostForm: false, - disablePagesScript: true, + disablePagesScript: false, enableInfiniteScroll: true, - fixedWidgetsPosition: false, useBlurEffectForModal: true, sidebarDisplay: 'full', // full, icon, hide roomGraphicsQuality: 'medium', @@ -98,152 +95,25 @@ function copy<T>(data: T): T { return JSON.parse(JSON.stringify(data)); } -export default () => new Vuex.Store({ +export const postFormActions = []; +export const userActions = []; +export const noteActions = []; +export const noteViewInterruptors = []; +export const notePostInterruptors = []; + +export const store = createStore({ + strict: _DEV_, + plugins: [createPersistedState({ paths: ['i', 'device', 'deviceUser', 'settings', 'instance'] })], state: { i: null, - pendingApiRequestsCount: 0, - spinner: null, - fullView: false, - - // Plugin - pluginContexts: new Map<string, AiScript>(), - postFormActions: [], - userActions: [], - noteActions: [], - noteViewInterruptors: [], - notePostInterruptors: [], }, getters: { isSignedIn: state => state.i != null, - - nav: (state, getters) => actions => ({ - notifications: { - title: 'notifications', - icon: faBell, - get show() { return getters.isSignedIn; }, - get indicated() { return getters.isSignedIn && state.i.hasUnreadNotification; }, - to: '/my/notifications', - }, - messaging: { - title: 'messaging', - icon: faComments, - get show() { return getters.isSignedIn; }, - get indicated() { return getters.isSignedIn && state.i.hasUnreadMessagingMessage; }, - to: '/my/messaging', - }, - drive: { - title: 'drive', - icon: faCloud, - get show() { return getters.isSignedIn; }, - to: '/my/drive', - }, - followRequests: { - title: 'followRequests', - icon: faUserClock, - get show() { return getters.isSignedIn && state.i.isLocked; }, - get indicated() { return getters.isSignedIn && state.i.hasPendingReceivedFollowRequest; }, - to: '/my/follow-requests', - }, - featured: { - title: 'featured', - icon: faFireAlt, - to: '/featured', - }, - explore: { - title: 'explore', - icon: faHashtag, - to: '/explore', - }, - announcements: { - title: 'announcements', - icon: faBroadcastTower, - get indicated() { return getters.isSignedIn && state.i.hasUnreadAnnouncement; }, - to: '/announcements', - }, - search: { - title: 'search', - icon: faSearch, - action: () => actions.search(), - }, - lists: { - title: 'lists', - icon: faListUl, - get show() { return getters.isSignedIn; }, - to: '/my/lists', - }, - groups: { - title: 'groups', - icon: faUsers, - get show() { return getters.isSignedIn; }, - to: '/my/groups', - }, - antennas: { - title: 'antennas', - icon: faSatellite, - get show() { return getters.isSignedIn; }, - to: '/my/antennas', - }, - mentions: { - title: 'mentions', - icon: faAt, - get show() { return getters.isSignedIn; }, - get indicated() { return getters.isSignedIn && state.i.hasUnreadMentions; }, - to: '/my/mentions', - }, - messages: { - title: 'directNotes', - icon: faEnvelope, - get show() { return getters.isSignedIn; }, - get indicated() { return getters.isSignedIn && state.i.hasUnreadSpecifiedNotes; }, - to: '/my/messages', - }, - favorites: { - title: 'favorites', - icon: faStar, - get show() { return getters.isSignedIn; }, - to: '/my/favorites', - }, - pages: { - title: 'pages', - icon: faFileAlt, - get show() { return getters.isSignedIn; }, - to: '/my/pages', - }, - channels: { - title: 'channel', - icon: faSatelliteDish, - to: '/channels', - }, - games: { - title: 'games', - icon: faGamepad, - to: '/games', - }, - scratchpad: { - title: 'scratchpad', - icon: faTerminal, - to: '/scratchpad', - }, - rooms: { - title: 'rooms', - icon: faDoorClosed, - get show() { return getters.isSignedIn; }, - get to() { return `/@${state.i.username}/room`; }, - }, - deck: { - title: deckmode ? 'undeck' : 'deck', - icon: faColumns, - action: () => { - localStorage.setItem('deckmode', (!deckmode).toString()); - location.reload(); - }, - }, - }), }, mutations: { @@ -254,56 +124,6 @@ export default () => new Vuex.Store({ updateIKeyValue(state, { key, value }) { state.i[key] = value; }, - - setFullView(state, v) { - state.fullView = v; - }, - - initPlugin(state, { plugin, aiscript }) { - state.pluginContexts.set(plugin.id, aiscript); - }, - - registerPostFormAction(state, { pluginId, title, handler }) { - state.postFormActions.push({ - title, handler: (form, update) => { - state.pluginContexts.get(pluginId).execFn(handler, [utils.jsToVal(form), values.FN_NATIVE(([key, value]) => { - update(key.value, value.value); - })]); - } - }); - }, - - registerUserAction(state, { pluginId, title, handler }) { - state.userActions.push({ - title, handler: (user) => { - state.pluginContexts.get(pluginId).execFn(handler, [utils.jsToVal(user)]); - } - }); - }, - - registerNoteAction(state, { pluginId, title, handler }) { - state.noteActions.push({ - title, handler: (note) => { - state.pluginContexts.get(pluginId).execFn(handler, [utils.jsToVal(note)]); - } - }); - }, - - registerNoteViewInterruptor(state, { pluginId, handler }) { - state.noteViewInterruptors.push({ - handler: (note) => { - return state.pluginContexts.get(pluginId).execFn(handler, [utils.jsToVal(note)]); - } - }); - }, - - registerNotePostInterruptor(state, { pluginId, handler }) { - state.notePostInterruptors.push({ - handler: (note) => { - return state.pluginContexts.get(pluginId).execFn(handler, [utils.jsToVal(note)]); - } - }); - }, }, actions: { @@ -349,47 +169,6 @@ export default () => new Vuex.Store({ ctx.commit('settings/init', me.clientData); } }, - - api(ctx, { endpoint, data, token }) { - if (++ctx.state.pendingApiRequestsCount === 1) { - // TODO: spinnerの表示はstoreでやらない - ctx.state.spinner = document.createElement('div'); - ctx.state.spinner.setAttribute('id', 'wait'); - document.body.appendChild(ctx.state.spinner); - } - - const onFinally = () => { - if (--ctx.state.pendingApiRequestsCount === 0) ctx.state.spinner.parentNode.removeChild(ctx.state.spinner); - }; - - const promise = new Promise((resolve, reject) => { - // Append a credential - if (ctx.getters.isSignedIn) (data as any).i = ctx.state.i.token; - if (token !== undefined) (data as any).i = token; - - // Send request - fetch(endpoint.indexOf('://') > -1 ? endpoint : `${apiUrl}/${endpoint}`, { - method: 'POST', - body: JSON.stringify(data), - credentials: 'omit', - cache: 'no-cache' - }).then(async (res) => { - const body = res.status === 204 ? null : await res.json(); - - if (res.status === 200) { - resolve(body); - } else if (res.status === 204) { - resolve(); - } else { - reject(body.error); - } - }).catch(reject); - }); - - promise.then(onFinally, onFinally); - - return promise; - } }, modules: { @@ -408,12 +187,9 @@ export default () => new Vuex.Store({ actions: { async fetch(ctx) { - const meta = await ctx.dispatch('api', { - endpoint: 'meta', - data: { - detail: false - } - }, { root: true }); + const meta = await api('meta', { + detail: false + }); ctx.commit('set', meta); } @@ -676,13 +452,10 @@ export default () => new Vuex.Store({ ctx.commit('set', x); if (ctx.rootGetters.isSignedIn) { - ctx.dispatch('api', { - endpoint: 'i/update-client-setting', - data: { - name: x.key, - value: x.value - } - }, { root: true }); + api('i/update-client-setting', { + name: x.key, + value: x.value + }); } }, } |