From ae2fbbef66d9aba150012027baf8b89bf79cd741 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=9C=D1=83=D1=84=D0=B0?= =?UTF-8?q?=D0=B7=D0=B0=D0=BB=D0=BE=D0=B2?= <67755036+artemmufazalov@users.noreply.github.com> Date: Thu, 28 Dec 2023 16:16:56 +0500 Subject: [PATCH] feat: migrate from external settings api (#621) --- src/containers/App/Content.js | 9 +- .../AsideNavigation/AsideNavigation.tsx | 39 ++---- .../Diagnostics/Partitions/Partitions.tsx | 5 +- .../Tenant/Query/QueryEditor/QueryEditor.js | 12 +- src/services/api.ts | 7 +- src/services/settings.ts | 113 ++++++++++++++++++ src/store/reducers/executeQuery.ts | 9 +- src/store/reducers/settings/settings.ts | 81 ++----------- src/store/reducers/settings/types.ts | 7 +- src/types/window.d.ts | 4 +- src/utils/hooks/useSetting.ts | 13 +- src/utils/i18n/i18n.ts | 4 +- src/utils/settings.ts | 13 -- 13 files changed, 166 insertions(+), 150 deletions(-) create mode 100644 src/services/settings.ts delete mode 100644 src/utils/settings.ts diff --git a/src/containers/App/Content.js b/src/containers/App/Content.js index 5c34fac3c..9fa23a6b4 100644 --- a/src/containers/App/Content.js +++ b/src/containers/App/Content.js @@ -16,8 +16,8 @@ import ReduxTooltip from '../ReduxTooltip/ReduxTooltip'; import Header from '../Header/Header'; import AppIcons from '../AppIcons/AppIcons'; -import {getParsedSettingValue} from '../../store/reducers/settings/settings'; import {THEME_KEY} from '../../utils/constants'; +import {useSetting} from '../../utils/hooks'; import './App.scss'; import PropTypes from 'prop-types'; @@ -72,7 +72,10 @@ Content.propTypes = { }; function ContentWrapper(props) { - const {theme, singleClusterMode, isAuthenticated} = props; + const {singleClusterMode, isAuthenticated} = props; + + const [theme] = useSetting(THEME_KEY); + return ( {(history) => ( @@ -96,7 +99,6 @@ function ContentWrapper(props) { } ContentWrapper.propTypes = { - theme: PropTypes.string, singleClusterMode: PropTypes.bool, isAuthenticated: PropTypes.bool, children: PropTypes.node, @@ -104,7 +106,6 @@ ContentWrapper.propTypes = { function mapStateToProps(state) { return { - theme: getParsedSettingValue(state, THEME_KEY), isAuthenticated: state.authentication.isAuthenticated, singleClusterMode: state.singleClusterMode, }; diff --git a/src/containers/AsideNavigation/AsideNavigation.tsx b/src/containers/AsideNavigation/AsideNavigation.tsx index e8a996089..8141d677a 100644 --- a/src/containers/AsideNavigation/AsideNavigation.tsx +++ b/src/containers/AsideNavigation/AsideNavigation.tsx @@ -1,5 +1,5 @@ import React, {useState} from 'react'; -import {connect} from 'react-redux'; +import {useDispatch} from 'react-redux'; import {useLocation} from 'react-router'; import {useHistory} from 'react-router-dom'; import cn from 'bem-cn-lite'; @@ -19,7 +19,6 @@ import settingsIcon from '../../assets/icons/settings.svg'; import supportIcon from '../../assets/icons/support.svg'; import {logout} from '../../store/reducers/authentication/authentication'; -import {getParsedSettingValue, setSettingValue} from '../../store/reducers/settings/settings'; import {TENANT_PAGE, TENANT_PAGES_IDS} from '../../store/reducers/tenant/constants'; import routes, {TENANT, createHref, parseQuery} from '../../routes'; import {useSetting, useTypedSelector} from '../../utils/hooks'; @@ -117,10 +116,6 @@ function YdbUserDropdown({isCompact, popupAnchor, ydbUser}: YdbUserDropdownProps interface AsideNavigationProps { children: React.ReactNode; - ydbUser: string; - compact: boolean; - logout: VoidFunction; - setSettingValue: (name: string, value: string) => void; } enum Panel { @@ -189,15 +184,19 @@ export const useGetLeftNavigationItems = () => { function AsideNavigation(props: AsideNavigationProps) { const history = useHistory(); + const dispatch = useDispatch(); const [visiblePanel, setVisiblePanel] = useState(); - const setIsCompact = (compact: boolean) => { - props.setSettingValue(ASIDE_HEADER_COMPACT_KEY, JSON.stringify(compact)); - }; + const {user: ydbUser} = useTypedSelector((state) => state.authentication); + const [compact, setIsCompact] = useSetting(ASIDE_HEADER_COMPACT_KEY); const menuItems = useGetLeftNavigationItems(); + const onLogout = () => { + dispatch(logout()); + }; + return ( history.push('/'), }} menuItems={menuItems} - compact={props.compact} + compact={compact} onChangeCompact={setIsCompact} className={b()} renderContent={() => props.children} @@ -248,8 +247,8 @@ function AsideNavigation(props: AsideNavigationProps) { isCompact={compact} popupAnchor={asideRef} ydbUser={{ - login: props.ydbUser, - logout: props.logout, + login: ydbUser, + logout: onLogout, }} /> @@ -269,18 +268,4 @@ function AsideNavigation(props: AsideNavigationProps) { ); } -const mapStateToProps = (state: any) => { - const {user: ydbUser} = state.authentication; - - return { - ydbUser, - compact: getParsedSettingValue(state, ASIDE_HEADER_COMPACT_KEY), - }; -}; - -const mapDispatchToProps = { - logout, - setSettingValue, -}; - -export default connect(mapStateToProps, mapDispatchToProps)(AsideNavigation); +export default AsideNavigation; diff --git a/src/containers/Tenant/Diagnostics/Partitions/Partitions.tsx b/src/containers/Tenant/Diagnostics/Partitions/Partitions.tsx index ecf305ca2..0e87ff9e6 100644 --- a/src/containers/Tenant/Diagnostics/Partitions/Partitions.tsx +++ b/src/containers/Tenant/Diagnostics/Partitions/Partitions.tsx @@ -70,10 +70,7 @@ export const Partitions = ({path}: PartitionsProps) => { error: nodesError, } = useTypedSelector((state) => state.nodesList); - const [hiddenColumns, setHiddenColumns] = useSetting( - PARTITIONS_HIDDEN_COLUMNS_KEY, - [], - ); + const [hiddenColumns, setHiddenColumns] = useSetting(PARTITIONS_HIDDEN_COLUMNS_KEY); const [columns, columnsIdsForSelector] = useGetPartitionsColumns(selectedConsumer); diff --git a/src/containers/Tenant/Query/QueryEditor/QueryEditor.js b/src/containers/Tenant/Query/QueryEditor/QueryEditor.js index 3770d4f51..4298a5a0a 100644 --- a/src/containers/Tenant/Query/QueryEditor/QueryEditor.js +++ b/src/containers/Tenant/Query/QueryEditor/QueryEditor.js @@ -17,7 +17,6 @@ import { setTenantPath, } from '../../../../store/reducers/executeQuery'; import {getExplainQuery, getExplainQueryAst} from '../../../../store/reducers/explainQuery'; -import {getParsedSettingValue, setSettingValue} from '../../../../store/reducers/settings/settings'; import {setShowPreview} from '../../../../store/reducers/schema/schema'; import { DEFAULT_IS_QUERY_RESULT_COLLAPSED, @@ -86,6 +85,7 @@ function QueryEditor(props) { const [queryMode, setQueryMode] = useQueryModes(); const [useMultiSchema] = useSetting(QUERY_USE_MULTI_SCHEMA_KEY); const [lastUsedQueryAction, setLastUsedQueryAction] = useSetting(LAST_USED_QUERY_ACTION_KEY); + const [savedQueries, setSavedQueries] = useSetting(SAVED_QUERIES_KEY); useEffect(() => { if (savedPath !== path) { @@ -417,7 +417,7 @@ function QueryEditor(props) { const storageEventHandler = (event) => { if (event.key === SAVED_QUERIES_KEY) { - props.setSettingValue(SAVED_QUERIES_KEY, event.newValue); + setSavedQueries(event.newValue); } }; @@ -430,8 +430,6 @@ function QueryEditor(props) { const onSaveQueryHandler = (queryName) => { const { executeQuery: {input}, - savedQueries = [], - setSettingValue, } = props; const queryIndex = savedQueries.findIndex( @@ -445,11 +443,11 @@ function QueryEditor(props) { newSavedQueries.push(newQuery); } - setSettingValue(SAVED_QUERIES_KEY, JSON.stringify(newSavedQueries)); + setSavedQueries(newSavedQueries); }; const renderControls = () => { - const {executeQuery, explainQuery, savedQueries} = props; + const {executeQuery, explainQuery} = props; return ( { return { executeQuery: state.executeQuery, explainQuery: state.explainQuery, - savedQueries: getParsedSettingValue(state, SAVED_QUERIES_KEY), showPreview: state.schema.showPreview, currentSchema: state.schema.currentSchema, monacoHotKey: state.executeQuery?.monacoHotKey, @@ -525,7 +522,6 @@ const mapDispatchToProps = { goToNextQuery, getExplainQuery, getExplainQueryAst, - setSettingValue, setShowPreview, setMonacoHotKey, setTenantPath, diff --git a/src/services/api.ts b/src/services/api.ts index 88c7038a9..22c9504a7 100644 --- a/src/services/api.ts +++ b/src/services/api.ts @@ -34,7 +34,6 @@ import type {StorageApiRequestParams} from '../store/reducers/storage/types'; import {backend as BACKEND} from '../store'; import {prepareSortValue} from '../utils/filters'; -import {settingsApi} from '../utils/settings'; const config = {withCredentials: !window.custom_backend}; @@ -378,10 +377,12 @@ export class YdbEmbeddedAPI extends AxiosWrapper { path_id: tenantId?.PathId, }); } - postSetting(name: string, value: string) { + + /** @deprecated use localStorage instead */ + postSetting(settingsApi: string, name: string, value: string) { return this.request({ method: 'PATCH', - url: settingsApi || '', + url: settingsApi, data: {[name]: value}, }); } diff --git a/src/services/settings.ts b/src/services/settings.ts new file mode 100644 index 000000000..49a751c64 --- /dev/null +++ b/src/services/settings.ts @@ -0,0 +1,113 @@ +import {TENANT_PAGES_IDS} from '../store/reducers/tenant/constants'; + +import { + ASIDE_HEADER_COMPACT_KEY, + CLUSTER_INFO_HIDDEN_KEY, + INVERTED_DISKS_KEY, + LANGUAGE_KEY, + LAST_USED_QUERY_ACTION_KEY, + PARTITIONS_HIDDEN_COLUMNS_KEY, + QUERY_INITIAL_MODE_KEY, + QUERY_USE_MULTI_SCHEMA_KEY, + SAVED_QUERIES_KEY, + TENANT_INITIAL_PAGE_KEY, + THEME_KEY, + USE_BACKEND_PARAMS_FOR_TABLES_KEY, + USE_NODES_ENDPOINT_IN_DIAGNOSTICS_KEY, +} from '../utils/constants'; +import {QUERY_ACTIONS, QUERY_MODES} from '../utils/query'; +import {parseJson} from '../utils/utils'; + +export type SettingsObject = Record; + +const USE_LOCAL_STORAGE_FOR_SETTINGS_KEY = 'useLocalStorageForSettings'; + +/** User settings keys and their default values */ +const DEFAULT_USER_SETTINGS: SettingsObject = { + [THEME_KEY]: 'system', + [LANGUAGE_KEY]: undefined, + [INVERTED_DISKS_KEY]: false, + [USE_NODES_ENDPOINT_IN_DIAGNOSTICS_KEY]: false, + [QUERY_USE_MULTI_SCHEMA_KEY]: false, + [SAVED_QUERIES_KEY]: [], + [TENANT_INITIAL_PAGE_KEY]: TENANT_PAGES_IDS.query, + [QUERY_INITIAL_MODE_KEY]: QUERY_MODES.script, + [LAST_USED_QUERY_ACTION_KEY]: QUERY_ACTIONS.execute, + [ASIDE_HEADER_COMPACT_KEY]: true, + [PARTITIONS_HIDDEN_COLUMNS_KEY]: [], + [CLUSTER_INFO_HIDDEN_KEY]: true, + [USE_BACKEND_PARAMS_FOR_TABLES_KEY]: false, +}; + +class SettingsManager { + constructor() { + // Migrate settings to LS if external API was used before + const settingsApi = window.web_version ? window.systemSettings?.settingsApi : undefined; + + const useLocalStorage = this.readUserSettingsValue(USE_LOCAL_STORAGE_FOR_SETTINGS_KEY); + + if (settingsApi && !useLocalStorage) { + const externalUserSettings = window.userSettings; + + if (externalUserSettings) { + Object.entries(externalUserSettings).forEach(([key, value]) => + this.setUserSettingsValue(key, value), + ); + } + + this.setUserSettingsValue(USE_LOCAL_STORAGE_FOR_SETTINGS_KEY, true); + } + } + + /** + * User settings - settings stored in LS or external store + */ + getUserSettings() { + return this.extractSettingsFromLS(); + } + + /** + * Returns parsed settings value. + * If value cannot be parsed, returns initially stored string. + * If there is no value, return default value + */ + readUserSettingsValue(key: string, defaultValue?: unknown) { + return this.readValueFromLS(key) ?? defaultValue ?? DEFAULT_USER_SETTINGS[key]; + } + + /** + * Stringify value and set it to LS + */ + setUserSettingsValue(key: string, value: unknown) { + return this.setValueToLS(key, value); + } + + private extractSettingsFromLS = () => { + return Object.entries(DEFAULT_USER_SETTINGS).reduce((acc, [key, value]) => { + acc[key] = this.readUserSettingsValue(key, value); + return acc; + }, {}); + }; + + private readValueFromLS = (key: string): unknown => { + try { + const value = localStorage.getItem(key); + + return parseJson(value); + } catch { + return undefined; + } + }; + + private setValueToLS = (key: string, value: unknown): void => { + try { + if (typeof value === 'string') { + localStorage.setItem(key, value); + } else { + localStorage.setItem(key, JSON.stringify(value)); + } + } catch {} + }; +} + +export const settingsManager = new SettingsManager(); diff --git a/src/store/reducers/executeQuery.ts b/src/store/reducers/executeQuery.ts index 3da042fb8..e34bb17ca 100644 --- a/src/store/reducers/executeQuery.ts +++ b/src/store/reducers/executeQuery.ts @@ -9,10 +9,10 @@ import type { QueryInHistory, } from '../../types/store/executeQuery'; import type {QueryRequestParams, QueryMode, QuerySyntax} from '../../types/store/query'; -import {getValueFromLS, parseJson} from '../../utils/utils'; import {QUERIES_HISTORY_KEY} from '../../utils/constants'; import {QUERY_MODES, QUERY_SYNTAX, parseQueryAPIExecuteResponse} from '../../utils/query'; import {parseQueryError} from '../../utils/error'; +import {settingsManager} from '../../services/settings'; import '../../services/api'; import {createRequestActionTypes, createApiRequest} from '../utils'; @@ -28,7 +28,10 @@ const GO_TO_NEXT_QUERY = 'query/GO_TO_NEXT_QUERY'; const SET_MONACO_HOT_KEY = 'query/SET_MONACO_HOT_KEY'; const SET_TENANT_PATH = 'query/SET_TENANT_PATH'; -const queriesHistoryInitial: string[] = parseJson(getValueFromLS(QUERIES_HISTORY_KEY, '[]')); +const queriesHistoryInitial = settingsManager.readUserSettingsValue( + QUERIES_HISTORY_KEY, + [], +) as string[]; const sliceLimit = queriesHistoryInitial.length - MAXIMUM_QUERIES_IN_HISTORY; @@ -97,7 +100,7 @@ const executeQuery: Reducer = ( const newQueries = [...state.history.queries, {queryText, syntax}].slice( state.history.queries.length >= MAXIMUM_QUERIES_IN_HISTORY ? 1 : 0, ); - window.localStorage.setItem(QUERIES_HISTORY_KEY, JSON.stringify(newQueries)); + settingsManager.setUserSettingsValue(QUERIES_HISTORY_KEY, newQueries); const currentIndex = newQueries.length - 1; return { diff --git a/src/store/reducers/settings/settings.ts b/src/store/reducers/settings/settings.ts index 48b43ac02..1502f38bf 100644 --- a/src/store/reducers/settings/settings.ts +++ b/src/store/reducers/settings/settings.ts @@ -1,32 +1,8 @@ import type {Reducer} from 'redux'; import type {ThunkAction} from 'redux-thunk'; -import { - SAVED_QUERIES_KEY, - THEME_KEY, - TENANT_INITIAL_PAGE_KEY, - INVERTED_DISKS_KEY, - ASIDE_HEADER_COMPACT_KEY, - USE_NODES_ENDPOINT_IN_DIAGNOSTICS_KEY, - PARTITIONS_HIDDEN_COLUMNS_KEY, - QUERY_INITIAL_MODE_KEY, - CLUSTER_INFO_HIDDEN_KEY, - LAST_USED_QUERY_ACTION_KEY, - USE_BACKEND_PARAMS_FOR_TABLES_KEY, - LANGUAGE_KEY, - QUERY_USE_MULTI_SCHEMA_KEY, -} from '../../../utils/constants'; import '../../../services/api'; -import {parseJson} from '../../../utils/utils'; -import {QUERY_ACTIONS, QUERY_MODES} from '../../../utils/query'; -import { - readSavedSettingsValue, - settingsApi, - systemSettings, - userSettings, -} from '../../../utils/settings'; - -import {TENANT_PAGES_IDS} from '../tenant/constants'; +import {settingsManager} from '../../../services/settings'; import type {RootState} from '..'; import type { @@ -45,39 +21,12 @@ export const ProblemFilterValues = { PROBLEMS: 'With problems', } as const; +const userSettings = settingsManager.getUserSettings(); +const systemSettings = window.systemSettings || {}; + export const initialState = { problemFilter: ProblemFilterValues.ALL, - userSettings: { - ...userSettings, - [THEME_KEY]: readSavedSettingsValue(THEME_KEY, 'system'), - [LANGUAGE_KEY]: readSavedSettingsValue(LANGUAGE_KEY), - [INVERTED_DISKS_KEY]: readSavedSettingsValue(INVERTED_DISKS_KEY, 'false'), - [USE_NODES_ENDPOINT_IN_DIAGNOSTICS_KEY]: readSavedSettingsValue( - USE_NODES_ENDPOINT_IN_DIAGNOSTICS_KEY, - 'false', - ), - [QUERY_USE_MULTI_SCHEMA_KEY]: readSavedSettingsValue(QUERY_USE_MULTI_SCHEMA_KEY, 'false'), - [SAVED_QUERIES_KEY]: readSavedSettingsValue(SAVED_QUERIES_KEY, '[]'), - [TENANT_INITIAL_PAGE_KEY]: readSavedSettingsValue( - TENANT_INITIAL_PAGE_KEY, - TENANT_PAGES_IDS.query, - ), - [QUERY_INITIAL_MODE_KEY]: readSavedSettingsValue( - QUERY_INITIAL_MODE_KEY, - QUERY_MODES.script, - ), - [LAST_USED_QUERY_ACTION_KEY]: readSavedSettingsValue( - LAST_USED_QUERY_ACTION_KEY, - QUERY_ACTIONS.execute, - ), - [ASIDE_HEADER_COMPACT_KEY]: readSavedSettingsValue(ASIDE_HEADER_COMPACT_KEY, 'true'), - [PARTITIONS_HIDDEN_COLUMNS_KEY]: readSavedSettingsValue(PARTITIONS_HIDDEN_COLUMNS_KEY), - [CLUSTER_INFO_HIDDEN_KEY]: readSavedSettingsValue(CLUSTER_INFO_HIDDEN_KEY, 'true'), - [USE_BACKEND_PARAMS_FOR_TABLES_KEY]: readSavedSettingsValue( - USE_BACKEND_PARAMS_FOR_TABLES_KEY, - 'false', - ), - }, + userSettings, systemSettings, }; @@ -108,19 +57,12 @@ const settings: Reducer = (state = initialState, export const setSettingValue = ( name: string, - value: string, + value: unknown, ): ThunkAction => { return (dispatch) => { dispatch({type: SET_SETTING_VALUE, data: {name, value}}); - // If there is no settingsApi, use localStorage - if (settingsApi) { - window.api.postSetting(name, value); - } else { - try { - localStorage.setItem(name, value); - } catch {} - } + settingsManager.setUserSettingsValue(name, value); }; }; @@ -128,15 +70,6 @@ export const getSettingValue = (state: SettingsRootStateSlice, name: string) => return state.settings.userSettings[name]; }; -/** - * Returns parsed settings value. - * If value cannot be parsed, returns initially stored string - */ -export const getParsedSettingValue = (state: SettingsRootStateSlice, name: string) => { - const value = state.settings.userSettings[name]; - return parseJson(value); -}; - export const changeFilter = (filter: ProblemFilterValue) => { return { type: CHANGE_PROBLEM_FILTER, diff --git a/src/store/reducers/settings/types.ts b/src/store/reducers/settings/types.ts index 2ac8e0a57..d89f7a56e 100644 --- a/src/store/reducers/settings/types.ts +++ b/src/store/reducers/settings/types.ts @@ -1,17 +1,18 @@ import type {ValueOf} from '../../../types/common'; +import type {SettingsObject} from '../../../services/settings'; import {changeFilter, ProblemFilterValues, SET_SETTING_VALUE} from './settings'; export type ProblemFilterValue = ValueOf; export interface SettingsState { problemFilter: ProblemFilterValue; - userSettings: Record; - systemSettings: Record; + userSettings: SettingsObject; + systemSettings: SettingsObject; } export type SetSettingValueAction = { type: typeof SET_SETTING_VALUE; - data: {name: string; value: string}; + data: {name: string; value: unknown}; }; export type SettingsAction = ReturnType | SetSettingValueAction; diff --git a/src/types/window.d.ts b/src/types/window.d.ts index eda038c26..fab283312 100644 --- a/src/types/window.d.ts +++ b/src/types/window.d.ts @@ -39,8 +39,8 @@ interface Window { __REDUX_DEVTOOLS_EXTENSION_COMPOSE__?: typeof import('redux').compose; store?: import('redux').Store; - userSettings?: Record; - systemSettings?: Record; + userSettings?: import('../services/settings').SettingsObject; + systemSettings?: import('../services/settings').SettingsObject; api: import('../services/api').YdbEmbeddedAPI; } diff --git a/src/utils/hooks/useSetting.ts b/src/utils/hooks/useSetting.ts index 49587db07..8cbf70295 100644 --- a/src/utils/hooks/useSetting.ts +++ b/src/utils/hooks/useSetting.ts @@ -1,22 +1,21 @@ import {useCallback} from 'react'; import {useDispatch} from 'react-redux'; -import {getParsedSettingValue, setSettingValue} from '../../store/reducers/settings/settings'; +import {getSettingValue, setSettingValue} from '../../store/reducers/settings/settings'; import {useTypedSelector} from './useTypedSelector'; export const useSetting = (key: string, defaultValue?: T): [T, (value: T) => void] => { const dispatch = useDispatch(); - const settingValue: T = useTypedSelector( - (state) => getParsedSettingValue(state, key) ?? defaultValue, - ); + const settingValue = useTypedSelector((state) => { + // Since we type setter value as T, we assume that received value is also T + return (getSettingValue(state, key) ?? defaultValue) as T; + }); const setValue = useCallback( (value: T) => { - const preparedValue = typeof value === 'string' ? value : JSON.stringify(value); - - dispatch(setSettingValue(key, preparedValue)); + dispatch(setSettingValue(key, value)); }, [dispatch, key], ); diff --git a/src/utils/i18n/i18n.ts b/src/utils/i18n/i18n.ts index 7e0fc782f..761b60517 100644 --- a/src/utils/i18n/i18n.ts +++ b/src/utils/i18n/i18n.ts @@ -3,7 +3,7 @@ import {configure as configureUiKit} from '@gravity-ui/uikit'; import {configure as configureYdbUiComponents} from 'ydb-ui-components'; import {LANGUAGE_KEY} from '../constants'; -import {readSavedSettingsValue} from '../settings'; +import {settingsManager} from '../../services/settings'; enum Lang { En = 'en', @@ -11,7 +11,7 @@ enum Lang { } const defaultLang = Lang.En; -const currentLang = readSavedSettingsValue(LANGUAGE_KEY, defaultLang); +const currentLang = settingsManager.readUserSettingsValue(LANGUAGE_KEY, defaultLang) as Lang; const i18n = new I18N(); diff --git a/src/utils/settings.ts b/src/utils/settings.ts deleted file mode 100644 index 81c62ce20..000000000 --- a/src/utils/settings.ts +++ /dev/null @@ -1,13 +0,0 @@ -import {getValueFromLS} from './utils'; - -export const userSettings = window.userSettings || {}; -export const systemSettings = window.systemSettings || {}; - -export const settingsApi = window.web_version ? systemSettings.settingsApi : undefined; - -export function readSavedSettingsValue(key: string, defaultValue?: string) { - // If there is no settingsApi, use localStorage - const savedValue = settingsApi ? userSettings[key] : getValueFromLS(key); - - return savedValue ?? defaultValue; -}