diff --git a/app/soapbox/actions/soapbox.js b/app/soapbox/actions/soapbox.js
index 2871e2aae..bc3bdc82f 100644
--- a/app/soapbox/actions/soapbox.js
+++ b/app/soapbox/actions/soapbox.js
@@ -2,6 +2,7 @@ import { Map as ImmutableMap, List as ImmutableList } from 'immutable';
import { createSelector } from 'reselect';
import { getHost } from 'soapbox/actions/instance';
+import { normalizeSoapboxConfig } from 'soapbox/normalizers';
import KVStore from 'soapbox/storage/kv_store';
import { getFeatures } from 'soapbox/utils/features';
@@ -33,79 +34,10 @@ const allowedEmojiRGI = ImmutableList([
'😩',
]);
-const year = new Date().getFullYear();
-
export const makeDefaultConfig = features => {
return ImmutableMap({
- logo: '',
- banner: '',
- brandColor: '', // Empty
- accentColor: '',
- colors: ImmutableMap({
- gray: ImmutableMap({
- 50: '#f9fafb',
- 100: '#f3f4f6',
- 200: '#e5e7eb',
- 300: '#d1d5db',
- 400: '#9ca3af',
- 500: '#6b7280',
- 600: '#4b5563',
- 700: '#374151',
- 800: '#1f2937',
- 900: '#111827',
- }),
- success: ImmutableMap({
- 50: '#f0fdf4',
- 100: '#dcfce7',
- 200: '#bbf7d0',
- 300: '#86efac',
- 400: '#4ade80',
- 500: '#22c55e',
- 600: '#16a34a',
- 700: '#15803d',
- 800: '#166534',
- 900: '#14532d',
- }),
- danger: ImmutableMap({
- 50: '#fef2f2',
- 100: '#fee2e2',
- 200: '#fecaca',
- 300: '#fca5a5',
- 400: '#f87171',
- 500: '#ef4444',
- 600: '#dc2626',
- 700: '#b91c1c',
- 800: '#991b1b',
- 900: '#7f1d1d',
- }),
- 'gradient-purple': '#b8a3f9',
- 'gradient-blue': '#9bd5ff',
- 'sea-blue': '#2feecc',
- }),
- customCss: ImmutableList(),
- promoPanel: ImmutableMap({
- items: ImmutableList(),
- }),
- extensions: ImmutableMap(),
- defaultSettings: ImmutableMap(),
- copyright: `♥${year}. Copying is an act of love. Please copy and share.`,
- navlinks: ImmutableMap({
- homeFooter: ImmutableList(),
- }),
allowedEmoji: features.emojiReactsRGI ? allowedEmojiRGI : allowedEmoji,
- verifiedIcon: '',
- verifiedCanEditName: false,
displayFqn: Boolean(features.federating),
- cryptoAddresses: ImmutableList(),
- cryptoDonatePanel: ImmutableMap({
- limit: 1,
- }),
- aboutPages: ImmutableMap(),
- betaPages: ImmutableMap(),
- mobilePages: ImmutableMap(),
- authenticatedProfile: true,
- singleUserMode: false,
- singleUserModeProfile: '',
});
};
@@ -114,7 +46,7 @@ export const getSoapboxConfig = createSelector([
state => getFeatures(state.get('instance')),
], (soapbox, features) => {
const defaultConfig = makeDefaultConfig(features);
- return soapbox.mergeDeepWith((o, n) => o || n, defaultConfig);
+ return normalizeSoapboxConfig(soapbox).merge(defaultConfig);
});
export function rememberSoapboxConfig(host) {
diff --git a/app/soapbox/components/media_gallery.js b/app/soapbox/components/media_gallery.js
index df1e4db42..2164031a8 100644
--- a/app/soapbox/components/media_gallery.js
+++ b/app/soapbox/components/media_gallery.js
@@ -157,8 +157,6 @@ class Item extends React.PureComponent {
);
} else if (attachment.get('type') === 'image') {
- const previewUrl = attachment.get('preview_url');
-
const originalUrl = attachment.get('url');
const letterboxed = shouldLetterbox(attachment);
@@ -169,7 +167,7 @@ class Item extends React.PureComponent {
onClick={this.handleClick}
target='_blank'
>
-
+
);
} else if (attachment.get('type') === 'gifv') {
diff --git a/app/soapbox/features/chats/index.js b/app/soapbox/features/chats/index.js
index d7e1036bc..ed8c35e60 100644
--- a/app/soapbox/features/chats/index.js
+++ b/app/soapbox/features/chats/index.js
@@ -8,7 +8,6 @@ import { fetchChats, launchChat } from 'soapbox/actions/chats';
import AccountSearch from 'soapbox/components/account_search';
import AudioToggle from 'soapbox/features/chats/components/audio_toggle';
-import ColumnHeader from '../../components/column_header';
import { Column } from '../../components/ui';
import ChatList from './components/chat_list';
@@ -47,11 +46,6 @@ class ChatIndex extends React.PureComponent {
return (
-
-
diff --git a/app/soapbox/features/crypto_donate/components/site_wallet.tsx b/app/soapbox/features/crypto_donate/components/site_wallet.tsx
index af5964796..1e09292bd 100644
--- a/app/soapbox/features/crypto_donate/components/site_wallet.tsx
+++ b/app/soapbox/features/crypto_donate/components/site_wallet.tsx
@@ -1,4 +1,3 @@
-import { trimStart } from 'lodash';
import React from 'react';
import { Stack } from 'soapbox/components/ui';
@@ -6,36 +5,22 @@ import { useSoapboxConfig } from 'soapbox/hooks';
import CryptoAddress from './crypto_address';
-import type { Map as ImmutableMap, List as ImmutableList } from 'immutable';
-
-type Address = ImmutableMap;
-
-// Address example:
-// {"ticker": "btc", "address": "bc1q9cx35adpm73aq2fw40ye6ts8hfxqzjr5unwg0n", "note": "This is our main address"}
-const normalizeAddress = (address: Address): Address => {
- return address.update('ticker', '', ticker => {
- return trimStart(ticker, '$').toLowerCase();
- });
-};
-
interface ISiteWallet {
limit?: number,
}
const SiteWallet: React.FC = ({ limit }): JSX.Element => {
- const addresses: ImmutableList =
- useSoapboxConfig().get('cryptoAddresses').map(normalizeAddress);
-
- const coinList = typeof limit === 'number' ? addresses.take(limit) : addresses;
+ const { cryptoAddresses } = useSoapboxConfig();
+ const addresses = typeof limit === 'number' ? cryptoAddresses.take(limit) : cryptoAddresses;
return (
- {coinList.map(coin => (
+ {addresses.map(address => (
))}
diff --git a/app/soapbox/features/soapbox_config/index.js b/app/soapbox/features/soapbox_config/index.js
index 84d80eea3..16cff42f3 100644
--- a/app/soapbox/features/soapbox_config/index.js
+++ b/app/soapbox/features/soapbox_config/index.js
@@ -12,8 +12,8 @@ import { connect } from 'react-redux';
import { updateConfig } from 'soapbox/actions/admin';
import { uploadMedia } from 'soapbox/actions/media';
import snackbar from 'soapbox/actions/snackbar';
-import { makeDefaultConfig } from 'soapbox/actions/soapbox';
import Icon from 'soapbox/components/icon';
+import { Column } from 'soapbox/components/ui';
import {
SimpleForm,
FieldsGroup,
@@ -26,10 +26,9 @@ import {
} from 'soapbox/features/forms';
import ThemeToggle from 'soapbox/features/ui/components/theme_toggle';
import { isMobile } from 'soapbox/is_mobile';
-import { getFeatures } from 'soapbox/utils/features';
+import { normalizeSoapboxConfig } from 'soapbox/normalizers';
import Accordion from '../ui/components/accordion';
-import Column from '../ui/components/column';
import IconPickerDropdown from './components/icon_picker_dropdown';
import SitePreview from './components/site_preview';
@@ -71,11 +70,8 @@ const templates = {
};
const mapStateToProps = state => {
- const instance = state.get('instance');
-
return {
- soapbox: state.get('soapbox'),
- features: getFeatures(instance),
+ initialData: state.soapbox,
};
};
@@ -84,37 +80,36 @@ export default @connect(mapStateToProps)
class SoapboxConfig extends ImmutablePureComponent {
static propTypes = {
- soapbox: ImmutablePropTypes.map.isRequired,
- features: PropTypes.object.isRequired,
+ initialData: ImmutablePropTypes.map.isRequired,
dispatch: PropTypes.func.isRequired,
intl: PropTypes.object.isRequired,
};
state = {
isLoading: false,
- soapbox: this.props.soapbox,
+ data: this.props.initialData,
jsonEditorExpanded: false,
rawJSON: JSON.stringify(this.props.soapbox, null, 2),
jsonValid: true,
}
setConfig = (path, value) => {
- const { soapbox } = this.state;
- const config = soapbox.setIn(path, value);
- this.setState({ soapbox: config, jsonValid: true });
+ const { data } = this.state;
+ const newData = data.setIn(path, value);
+ this.setState({ data: newData, jsonValid: true });
};
- putConfig = config => {
- this.setState({ soapbox: config, jsonValid: true });
+ putConfig = data => {
+ this.setState({ data, jsonValid: true });
};
getParams = () => {
- const { soapbox } = this.state;
+ const { data } = this.state;
return [{
group: ':pleroma',
key: ':frontend_configurations',
value: [{
- tuple: [':soapbox_fe', soapbox.toJS()],
+ tuple: [':soapbox_fe', data.toJS()],
}],
}];
}
@@ -158,8 +153,8 @@ class SoapboxConfig extends ImmutablePureComponent {
handleDeleteItem = path => {
return e => {
- const soapbox = this.state.soapbox.deleteIn(path);
- this.setState({ soapbox });
+ const data = this.state.data.deleteIn(path);
+ this.setState({ data });
};
};
@@ -195,20 +190,18 @@ class SoapboxConfig extends ImmutablePureComponent {
}
getSoapboxConfig = () => {
- const { features } = this.props;
- const { soapbox } = this.state;
- return makeDefaultConfig(features).mergeDeep(soapbox);
+ return normalizeSoapboxConfig(this.state.data);
}
toggleJSONEditor = (value) => this.setState({ jsonEditorExpanded: value });
componentDidUpdate(prevProps, prevState) {
- if (prevProps.soapbox !== this.props.soapbox) {
- this.putConfig(this.props.soapbox);
+ if (prevProps.initialData !== this.props.initialData) {
+ this.putConfig(this.props.initialData);
}
- if (prevState.soapbox !== this.state.soapbox) {
- this.setState({ rawJSON: JSON.stringify(this.state.soapbox, null, 2) });
+ if (prevState.data !== this.state.data) {
+ this.setState({ rawJSON: JSON.stringify(this.state.data, null, 2) });
}
if (prevState.rawJSON !== this.state.rawJSON) {
@@ -226,7 +219,7 @@ class SoapboxConfig extends ImmutablePureComponent {
const soapbox = this.getSoapboxConfig();
return (
-
+