Little refactoring of the accounts API for the frontend application

This commit is contained in:
ErickSkrauch 2019-01-25 20:29:32 +03:00
parent 4727e0d88a
commit afde68ae5b
3 changed files with 110 additions and 97 deletions

View File

@ -1,4 +1,8 @@
import accounts from 'services/api/accounts'; import {
getInfo as getInfoEndpoint,
changeLang as changeLangEndpoint,
acceptRules as acceptRulesEndpoint,
} from 'services/api/accounts';
import { setLocale } from 'components/i18n/actions'; import { setLocale } from 'components/i18n/actions';
export const UPDATE = 'USER_UPDATE'; export const UPDATE = 'USER_UPDATE';
@ -36,7 +40,7 @@ export function changeLang(lang) {
const {user: {isGuest, lang: oldLang}} = getState(); const {user: {isGuest, lang: oldLang}} = getState();
if (oldLang !== lang) { if (oldLang !== lang) {
!isGuest && accounts.changeLang(lang); !isGuest && changeLangEndpoint(lang);
dispatch({ dispatch({
type: CHANGE_LANG, type: CHANGE_LANG,
@ -59,7 +63,7 @@ export function setGuest() {
export function fetchUserData() { export function fetchUserData() {
return (dispatch) => return (dispatch) =>
accounts.current() getInfoEndpoint(0)
.then((resp) => { .then((resp) => {
dispatch(updateUser({ dispatch(updateUser({
isGuest: false, isGuest: false,
@ -72,7 +76,7 @@ export function fetchUserData() {
export function acceptRules() { export function acceptRules() {
return (dispatch) => return (dispatch) =>
accounts.acceptRules().then((resp) => { acceptRulesEndpoint().then((resp) => {
dispatch(updateUser({ dispatch(updateUser({
shouldAcceptRules: false shouldAcceptRules: false
})); }));

View File

@ -1,7 +1,7 @@
// @flow // @flow
import request from 'services/request'; import request from 'services/request';
type UserResponse = { export type UserResponse = {
elyProfileLink: string, elyProfileLink: string,
email: string, email: string,
hasMojangUsernameCollision: bool, hasMojangUsernameCollision: bool,
@ -16,6 +16,79 @@ type UserResponse = {
uuid: string, uuid: string,
}; };
export function getInfo(id: number, options: { token?: ?string } = {}): Promise<UserResponse> {
return request.get(`/api/v1/accounts/${id}`, {}, {
token: options.token,
});
}
export function changePassword({
password = '',
newPassword = '',
newRePassword = '',
logoutAll = true,
}: {
password?: string,
newPassword?: string,
newRePassword?: string,
logoutAll?: bool,
}) {
return request.post('/api/accounts/change-password', {
password,
newPassword,
newRePassword,
logoutAll,
});
}
export function acceptRules() {
return request.post('/api/accounts/accept-rules');
}
export function changeUsername({
username = '',
password = '',
}: {
username?: string,
password?: string,
}) {
return request.post('/api/accounts/change-username', {
username,
password,
});
}
export function changeLang(lang: string) {
return request.post('/api/accounts/change-lang', {
lang,
});
}
export function requestEmailChange({ password = '' }: { password?: string }) {
return request.post('/api/accounts/change-email/initialize', {
password,
});
}
export function setNewEmail({
email = '',
key = '',
}: {
email?: string,
key?: string,
}) {
return request.post('/api/accounts/change-email/submit-new-email', {
email,
key,
});
}
export function confirmNewEmail({ key }: { key: string }) {
return request.post('/api/accounts/change-email/confirm-new-email', {
key,
});
}
export default { export default {
/** /**
* @param {object} options * @param {object} options
@ -25,76 +98,8 @@ export default {
* @return {Promise<UserResponse>} * @return {Promise<UserResponse>}
*/ */
current(options: { token?: ?string } = {}): Promise<UserResponse> { current(options: { token?: ?string } = {}): Promise<UserResponse> {
return request.get('/api/accounts/current', {}, { return getInfo(0, options);
token: options.token
});
}, },
changePassword({
password = '',
newPassword = '',
newRePassword = '',
logoutAll = true
}: {
password?: string,
newPassword?: string,
newRePassword?: string,
logoutAll?: bool,
}) {
return request.post(
'/api/accounts/change-password',
{password, newPassword, newRePassword, logoutAll}
);
},
acceptRules() {
return request.post('/api/accounts/accept-rules');
},
changeUsername({
username = '',
password = ''
}: {
username?: string,
password?: string,
}) {
return request.post(
'/api/accounts/change-username',
{username, password}
);
},
changeLang(lang: string) {
return request.post(
'/api/accounts/change-lang',
{lang}
);
},
requestEmailChange({password = ''}: { password?: string }) {
return request.post(
'/api/accounts/change-email/initialize',
{password}
);
},
setNewEmail({
email = '',
key = ''
}: {
email?: string,
key?: string,
}) {
return request.post(
'/api/accounts/change-email/submit-new-email',
{email, key}
);
},
confirmNewEmail({key}: { key: string }) {
return request.post(
'/api/accounts/change-email/confirm-new-email',
{key}
);
}
}; };

View File

@ -1,7 +1,8 @@
// @flow // @flow
import type { UserResponse } from 'services/api/accounts';
import logger from 'services/logger'; import logger from 'services/logger';
import request, { InternalServerError } from 'services/request'; import request, { InternalServerError } from 'services/request';
import accounts from 'services/api/accounts'; import { getInfo as getInfoEndpoint } from 'services/api/accounts';
const authentication = { const authentication = {
login({ login({
@ -70,35 +71,38 @@ const authentication = {
/** /**
* Resolves if token is valid * Resolves if token is valid
* *
* @param {object} options * @param {string} token
* @param {string} options.token * @param {string} refreshToken
* @param {string} options.refreshToken
* *
* @return {Promise} - resolves with options.token or with a new token * @return {Promise} - resolves with options.token or with a new token
* if it was refreshed. As a side effect the response * if it was refreshed. As a side effect the response
* will have a `user` field with current user data * will have a `user` field with current user data
*
*/ */
validateToken({token, refreshToken}: { async validateToken(token: string, refreshToken: ?string): Promise<{
token: string, token: string,
refreshToken: ?string refreshToken: ?string,
}) { user: UserResponse,
return new Promise((resolve) => { }> {
if (typeof token !== 'string') { if (typeof token !== 'string') {
throw new Error('token must be a string'); throw new Error('token must be a string');
} }
resolve(); // TODO: decode token to extract information about user id
})
.then(() => accounts.current({token})) let user: UserResponse;
.then((user) => ({token, refreshToken, user})) try {
.catch((resp) => user = await getInfoEndpoint(0, { token });
this.handleTokenError(resp, refreshToken) } catch (resp) {
// TODO: use recursion here const { token } = await this.handleTokenError(resp, refreshToken);
.then(({token}) => user = await getInfoEndpoint(0, { token }); // TODO: replace with recursive call
accounts.current({token}) }
.then((user) => ({token, refreshToken, user}))
) return {
); token,
refreshToken,
user,
};
}, },
handleTokenError(resp: Error | { message: string }, refreshToken: ?string): Promise<{ handleTokenError(resp: Error | { message: string }, refreshToken: ?string): Promise<{