From c5aa3037935764a425aab4489648940ec81ee527 Mon Sep 17 00:00:00 2001 From: SleepWalker Date: Thu, 12 Jan 2017 08:12:56 +0200 Subject: [PATCH] #246: remove User class in favor of plain object in reducer --- src/components/accounts/actions.js | 11 ++--- src/components/user/User.js | 74 ++++++------------------------ src/components/user/reducer.js | 43 +++++++++++++---- 3 files changed, 52 insertions(+), 76 deletions(-) diff --git a/src/components/accounts/actions.js b/src/components/accounts/actions.js index a76eecb..a088aac 100644 --- a/src/components/accounts/actions.js +++ b/src/components/accounts/actions.js @@ -1,18 +1,17 @@ import { routeActions } from 'react-router-redux'; import authentication from 'services/api/authentication'; -import accounts from 'services/api/accounts'; import { updateUser, setGuest } from 'components/user/actions'; import { setLocale } from 'components/i18n/actions'; import logger from 'services/logger'; /** * @typedef {object} Account - * @property {string} account.id - * @property {string} account.username - * @property {string} account.email - * @property {string} account.token - * @property {string} account.refreshToken + * @property {string} id + * @property {string} username + * @property {string} email + * @property {string} token + * @property {string} refreshToken */ /** diff --git a/src/components/user/User.js b/src/components/user/User.js index b56c548..6c0ae39 100644 --- a/src/components/user/User.js +++ b/src/components/user/User.js @@ -1,66 +1,18 @@ import { PropTypes } from 'react'; -const KEY_USER = 'user'; - -export default class User { - /** - * @param {object} [data] - plain object or jwt token or empty to load from storage - * - * @return {User} - */ - constructor(data) { - if (!data) { - return this.load(); - } - - // TODO: strict value types validation - - const defaults = { - id: null, - uuid: null, - username: '', - email: '', - // will contain user's email or masked email - // (e.g. ex**ple@em*il.c**) depending on what information user have already provided - maskedEmail: '', - avatar: '', - lang: '', - isActive: false, - shouldAcceptRules: false, // whether user need to review updated rules - passwordChangedAt: null, - hasMojangUsernameCollision: false, - - // frontend app specific attributes - isGuest: true, - goal: null, // the goal with wich user entered site - - // TODO: remove me after migration to multy accs - token: '', - refreshToken: '' - }; - - const user = Object.keys(defaults).reduce((user, key) => { - if (data.hasOwnProperty(key)) { - user[key] = data[key]; - } - - return user; - }, defaults); - - localStorage.setItem(KEY_USER, JSON.stringify(user)); - - return user; - } - - load() { - try { - return new User(JSON.parse(localStorage.getItem(KEY_USER))); - } catch (error) { - return new User({isGuest: true}); - } - } -} - +/** + * @typedef {object} User + * @property {number} id + * @property {string} uuid + * @property {string} token + * @property {string} username + * @property {string} email + * @property {string} avatar + * @property {bool} isGuest + * @property {bool} isActive + * @property {number} passwordChangedAt - timestamp + * @property {bool} hasMojangUsernameCollision + */ export const userShape = PropTypes.shape({ id: PropTypes.number, uuid: PropTypes.string, diff --git a/src/components/user/reducer.js b/src/components/user/reducer.js index b107027..e4e020f 100644 --- a/src/components/user/reducer.js +++ b/src/components/user/reducer.js @@ -1,10 +1,28 @@ import { UPDATE, SET, CHANGE_LANG } from './actions'; -import User from './User'; -// TODO: возможно есть смысл инитить обьект User снаружи, так как редусер не должен столько знать +const defaults = { + id: null, + uuid: null, + username: '', + email: '', + // will contain user's email or masked email + // (e.g. ex**ple@em*il.c**) depending on what information user have already provided + maskedEmail: '', + avatar: '', + lang: '', + isActive: false, + shouldAcceptRules: false, // whether user need to review updated rules + passwordChangedAt: null, + hasMojangUsernameCollision: false, + + // frontend specific attributes + isGuest: true, + goal: null // the goal with wich user entered site +}; + export default function user( - state = new User(), + state = null, {type, payload = null} ) { switch (type) { @@ -13,25 +31,32 @@ export default function user( throw new Error('payload.lang is required for user reducer'); } - return new User({ + return { ...state, lang: payload.lang - }); + }; case UPDATE: if (!payload) { throw new Error('payload is required for user reducer'); } - return new User({ + return { ...state, ...payload - }); + }; case SET: - return new User(payload || {}); + payload = payload || {}; + + return { + ...defaults, + ...payload + }; default: - return state; + return state || { + ...defaults + }; } }