settings on redux; some fix with theme

This commit is contained in:
2020-10-15 00:34:37 +03:00
parent 5d137eb603
commit 19e023c80f
9 changed files with 75 additions and 35 deletions
+10 -6
View File
@@ -26,11 +26,13 @@ import Users from "../Users/Users";
import {getVersion, version} from "../../api/api";
import Settings from "../User/Settings/Settings";
import {setUser} from "../../store/ducks/currentUser";
import {setSettings} from "../../store/ducks/userSettings";
type Props = {
notifications: React.ReactNode[]
setUser: (user: UserType) => void
modal: React.ReactNode
setUser: SetUser
setSettings: SetSettings
};
type State = {}
@@ -45,10 +47,11 @@ class App extends React.Component<Props, State> {
if(cachedTheme)
document.body.setAttribute('theme', cachedTheme);
const { setUser } = props;
fetchCurrentUser().then((user: UserType) => {
const { setUser, setSettings } = props;
fetchCurrentUser().then(user => {
setUser(user);
fetchUserSettings().then((settings: UserSettingsType) => {
fetchUserSettings().then(settings => {
setSettings(settings);
if(settings.theme !== cachedTheme) {
localStorage.setItem('theme', settings.theme);
document.body.setAttribute('theme', settings.theme);
@@ -64,7 +67,7 @@ class App extends React.Component<Props, State> {
getVersion().then(res => {
if(version !== res.version) {
console.log(`Current back-end version: ${res.version}. Clearing cache`);
console.debug(`Current back-end version: ${res.version}. Clearing cache`);
caches.keys().then(names => {
names.forEach(name => caches.delete(name).catch(console.error))
@@ -130,6 +133,7 @@ export default connect(
modal: state.modal
}),
dispatch => ({
setUser: (userData: UserType) => dispatch(setUser(userData))
setUser: (userData: UserType) => dispatch(setUser(userData)),
setSettings: (settings: UserSettingsType) => dispatch(setSettings(settings))
})
)(App);
+16 -7
View File
@@ -13,12 +13,15 @@ import Input from "../../ui/Input/Input";
import {setUser} from "../../store/ducks/currentUser";
import {addNotification} from "../../store/ducks/notifications";
import {hideModal, setModal} from "../../store/ducks/modal";
import {fetchUserSettings} from "../../api/users";
import {setSettings} from "../../store/ducks/userSettings";
type Props = {
setUser: (user: UserType) => void
addNotification: (notification: React.ReactNode) => void
setModal: (modal: React.ReactNode | null) => void
hideModal: () => void
setUser: SetUser
addNotification: AddNotification
setModal: SetModal
hideModal: HideModal
setSettings: SetSettings
};
type State = {
@@ -36,7 +39,7 @@ class LoginModal extends React.Component<Props, State> {
loginAndFetchToken = (event: FormEvent) => {
event.preventDefault();
const { setUser, addNotification, setModal } = this.props;
const { setUser, addNotification, setModal, setSettings } = this.props;
const { login: log, password, recaptcha } = this.state;
login(log, password, recaptcha).then(user => {
@@ -50,8 +53,13 @@ class LoginModal extends React.Component<Props, State> {
);
addNotification(successful);
setModal(null);
})
.catch((r: ApiError) => {
fetchUserSettings().then(settings => {
localStorage.setItem('theme', settings.theme);
document.body.setAttribute('theme', settings.theme);
setSettings(settings);
});
}).catch((r: ApiError) => {
this.setState({ error: errors[r.code] });
if(r.code === 9) this.setState({ recaptchaNeeded: true });
});
@@ -105,6 +113,7 @@ class LoginModal extends React.Component<Props, State> {
export default connect(null,
dispatch => ({
setUser: (user: UserType) => dispatch(setUser(user)),
setSettings: (settings: UserSettingsType) => dispatch(setSettings(settings)),
addNotification: (notification: React.ReactNode) => dispatch(addNotification(notification)),
setModal: (modal: React.ReactNode | null) => dispatch(setModal(modal)),
hideModal: () => dispatch(hideModal())
+3 -1
View File
@@ -30,7 +30,9 @@ class Navbar extends React.Component<Props, State> {
logout = () => {
this.props.logout();
localStorage.removeItem('user');
userLogout().then();
localStorage.removeItem('theme');
document.querySelector('body')!!.removeAttribute('theme');
userLogout().catch(() => {});
};
changeSize = () => {
+7 -9
View File
@@ -1,12 +1,13 @@
import Button from "../../../ui/Button/Button";
import Group from "../../../ui/Group/Group";
import React, {FormEvent} from "react";
import {fetchUserSettings, updateUserAppearanceSettings} from "../../../api/users";
import {updateUserAppearanceSettings} from "../../../api/users";
import {connect} from "react-redux";
import {setUser} from "../../../store/ducks/currentUser";
type Props = {
setUser: SetUser
settings: UserSettingsType
}
type State = {
@@ -15,13 +16,7 @@ type State = {
class Appearance extends React.Component<Props, State> {
state: State = {
theme: 'dark'
}
componentDidMount() {
fetchUserSettings().then(settings => {
this.setState({ theme: settings.theme })
})
theme: this.props.settings.theme
}
saveTheme = (event: FormEvent) => {
@@ -59,7 +54,10 @@ class Appearance extends React.Component<Props, State> {
}
}
export default connect(null,
export default connect(
(state: StoreState) => ({
settings: state.userSettings
}),
dispatch => ({
setUser: (user: UserType) => dispatch(setUser(user))
})
+10 -10
View File
@@ -1,10 +1,12 @@
import React, {ChangeEvent, FormEvent} from "react";
import Button from "../../../ui/Button/Button";
import Group from "../../../ui/Group/Group";
import {fetchUserSettings, updateUserGeneralSettings, uploadAvatar} from "../../../api/users";
import {updateUserGeneralSettings, uploadAvatar} from "../../../api/users";
import {connect} from "react-redux";
type Props = {
setUser: (user: UserType) => void
setUser: SetUser
settings: UserSettingsType
}
type State = {
@@ -15,13 +17,7 @@ type State = {
class General extends React.Component<Props, State> {
state: State = {
useGravatar: false, avatar: null
}
componentDidMount() {
fetchUserSettings().then(settings => {
this.setState({ useGravatar: settings.use_gravatar })
})
useGravatar: this.props.settings.use_gravatar, avatar: null
}
onChangeAvatar = (event: ChangeEvent<HTMLInputElement>) => {
@@ -62,4 +58,8 @@ class General extends React.Component<Props, State> {
}
}
export default General;
export default connect(
(state: StoreState) => ({
settings: state.userSettings
})
)(General);
+1 -1
View File
@@ -55,7 +55,7 @@ class Security extends React.Component<{}, State> {
placeholder={'Новый E-mail ещё раз'}
type={'email'}
value={email2}
onChange={e => this.setState({ email1: e.target.value })}
onChange={e => this.setState({ email2: e.target.value })}
/>
<Button>Сохранить</Button>
</form>
+2 -1
View File
@@ -2,5 +2,6 @@ import {combineReducers} from "redux";
import currentUser from './currentUser'
import modal from "./modal";
import notifications from './notifications'
import userSettings from './userSettings';
export default combineReducers({ currentUser, modal, notifications })
export default combineReducers({ currentUser, modal, notifications, userSettings })
+19
View File
@@ -0,0 +1,19 @@
const SET_SETTINGS = 'unmei/userSettings/SET_SETTINGS';
const reducer = (state={}, action: Action<{settings: UserSettingsType}>) => {
switch (action.type) {
case SET_SETTINGS:
state = Object.assign({}, state, action.payload.settings);
return state;
default:
return state;
}
}
const setSettings = (settings: UserSettingsType) => ({
type: SET_SETTINGS,
payload: { settings }
});
export default reducer;
export { setSettings }
+7
View File
@@ -1,11 +1,18 @@
type StoreState = {
currentUser: UserType
userSettings: UserSettingsType
notifications: React.ReactNode[]
modal: React.ReactNode
}
type Action<T> = {
type: string
payload: T
}
type SetUser = (user: UserType) => void
type LogoutUser = () => void
type SetSettings = (settings: UserSettingsType) => void
type SetModal = (modal: React.ReactNode | null) => void
type HideModal = () => void
type AddNotification = (notification: React.ReactNode) => void