mirror of
https://github.com/trezor/trezor-wallet
synced 2024-11-28 03:08:30 +00:00
implement RouterActions in services and other actions
This commit is contained in:
parent
8009ec647f
commit
900c3961cd
@ -6,8 +6,7 @@ import * as CONNECT from 'actions/constants/TrezorConnect';
|
|||||||
import * as NOTIFICATION from 'actions/constants/notification';
|
import * as NOTIFICATION from 'actions/constants/notification';
|
||||||
import * as WALLET from 'actions/constants/wallet';
|
import * as WALLET from 'actions/constants/wallet';
|
||||||
import { getDuplicateInstanceNumber } from 'reducers/utils';
|
import { getDuplicateInstanceNumber } from 'reducers/utils';
|
||||||
|
import * as RouterActions from 'actions/RouterActions';
|
||||||
import { push } from 'react-router-redux';
|
|
||||||
|
|
||||||
import type {
|
import type {
|
||||||
DeviceMessage,
|
DeviceMessage,
|
||||||
@ -79,14 +78,6 @@ export type TrezorConnectAction = {
|
|||||||
type: typeof CONNECT.STOP_ACQUIRING,
|
type: typeof CONNECT.STOP_ACQUIRING,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
const sortDevices = (devices: Array<TrezorDevice>): Array<TrezorDevice> => devices.sort((a, b) => {
|
|
||||||
if (!a.ts || !b.ts) {
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
return a.ts > b.ts ? -1 : 1;
|
|
||||||
});
|
|
||||||
|
|
||||||
export const init = (): AsyncAction => async (dispatch: Dispatch, getState: GetState): Promise<void> => {
|
export const init = (): AsyncAction => async (dispatch: Dispatch, getState: GetState): Promise<void> => {
|
||||||
// set listeners
|
// set listeners
|
||||||
TrezorConnect.on(DEVICE_EVENT, (event: DeviceMessage): void => {
|
TrezorConnect.on(DEVICE_EVENT, (event: DeviceMessage): void => {
|
||||||
@ -132,7 +123,7 @@ export const init = (): AsyncAction => async (dispatch: Dispatch, getState: GetS
|
|||||||
try {
|
try {
|
||||||
await TrezorConnect.init({
|
await TrezorConnect.init({
|
||||||
transportReconnect: true,
|
transportReconnect: true,
|
||||||
debug: true,
|
debug: false,
|
||||||
popup: false,
|
popup: false,
|
||||||
webusb: true,
|
webusb: true,
|
||||||
pendingTransportEvent: (getState().devices.length < 1),
|
pendingTransportEvent: (getState().devices.length < 1),
|
||||||
@ -145,67 +136,11 @@ export const init = (): AsyncAction => async (dispatch: Dispatch, getState: GetS
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// selection from Aside dropdown button
|
|
||||||
// after device_connect event
|
|
||||||
// or after acquiring device
|
|
||||||
// device type could be local TrezorDevice or Device (from trezor-connect device_connect event)
|
|
||||||
export const onSelectDevice = (device: TrezorDevice | Device): ThunkAction => (dispatch: Dispatch, getState: GetState): void => {
|
|
||||||
// || device.isUsedElsewhere
|
|
||||||
|
|
||||||
// switch to initial url and reset this value
|
|
||||||
|
|
||||||
if (!device.features) {
|
|
||||||
dispatch(push(`/device/${device.path}/${device.type === 'unreadable' ? 'unreadable' : 'acquire'}`));
|
|
||||||
} else if (device.features.bootloader_mode) {
|
|
||||||
dispatch(push(`/device/${device.path}/bootloader`));
|
|
||||||
} else if (!device.features.initialized) {
|
|
||||||
dispatch(push(`/device/${device.features.device_id}/initialize`));
|
|
||||||
} else if (typeof device.instance === 'number') {
|
|
||||||
dispatch(push(`/device/${device.features.device_id}:${device.instance}`));
|
|
||||||
} else {
|
|
||||||
const deviceId: string = device.features.device_id;
|
|
||||||
const urlParams: RouterLocationState = getState().router.location.state;
|
|
||||||
// let url: string = `/device/${ device.features.device_id }/network/ethereum/account/0`;
|
|
||||||
let url: string = `/device/${deviceId}`;
|
|
||||||
let instance: ?number;
|
|
||||||
// check if device is not TrezorDevice type
|
|
||||||
if (!device.hasOwnProperty('ts')) {
|
|
||||||
// its device from trezor-connect (called in initConnectedDevice triggered by device_connect event)
|
|
||||||
// need to lookup if there are unavailable instances
|
|
||||||
const available: Array<TrezorDevice> = getState().devices.filter(d => d.path === device.path);
|
|
||||||
const latest: Array<TrezorDevice> = sortDevices(available);
|
|
||||||
|
|
||||||
if (latest.length > 0 && latest[0].instance) {
|
|
||||||
url += `:${latest[0].instance}`;
|
|
||||||
instance = latest[0].instance;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// check if current location is not set to this device
|
|
||||||
//dispatch( push(`/device/${ device.features.device_id }/network/etc/account/0`) );
|
|
||||||
|
|
||||||
if (urlParams.deviceInstance !== instance || urlParams.device !== deviceId) {
|
|
||||||
dispatch(push(url));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
export const initConnectedDevice = (device: TrezorDevice | Device): ThunkAction => (dispatch: Dispatch/* , getState: GetState */): void => {
|
|
||||||
// const selected = getState().wallet.selectedDevice;
|
|
||||||
// if (!selected || (selected && selected.state)) {
|
|
||||||
dispatch(onSelectDevice(device));
|
|
||||||
// }
|
|
||||||
// if (device.unacquired && selected && selected.path !== device.path && !selected.connected) {
|
|
||||||
// dispatch( onSelectDevice(device) );
|
|
||||||
// } else if (!selected) {
|
|
||||||
// dispatch( onSelectDevice(device) );
|
|
||||||
// }
|
|
||||||
};
|
|
||||||
|
|
||||||
// called after backend was initialized
|
// called after backend was initialized
|
||||||
// set listeners for connect/disconnect
|
// set listeners for connect/disconnect
|
||||||
export const postInit = (): ThunkAction => (dispatch: Dispatch, getState: GetState): void => {
|
export const postInit = (): ThunkAction => (dispatch: Dispatch, getState: GetState): void => {
|
||||||
const handleDeviceConnect = (device: Device) => {
|
const handleDeviceConnect = (device: Device) => {
|
||||||
dispatch(initConnectedDevice(device));
|
dispatch( RouterActions.selectDevice(device) );
|
||||||
};
|
};
|
||||||
|
|
||||||
TrezorConnect.off(DEVICE.CONNECT, handleDeviceConnect);
|
TrezorConnect.off(DEVICE.CONNECT, handleDeviceConnect);
|
||||||
@ -216,56 +151,13 @@ export const postInit = (): ThunkAction => (dispatch: Dispatch, getState: GetSta
|
|||||||
|
|
||||||
const { devices } = getState();
|
const { devices } = getState();
|
||||||
|
|
||||||
const { initialPathname, initialParams } = getState().wallet;
|
// try to redirect to initial url
|
||||||
|
if (!dispatch( RouterActions.setInitialUrl() )) {
|
||||||
if (initialPathname) {
|
// if initial redirection fails try to switch to first available device
|
||||||
dispatch({
|
dispatch( RouterActions.selectFirstAvailableDevice() )
|
||||||
type: WALLET.SET_INITIAL_URL,
|
|
||||||
// pathname: null,
|
|
||||||
// params: null
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
if (devices.length > 0) {
|
|
||||||
const unacquired: ?TrezorDevice = devices.find(d => d.features);
|
|
||||||
if (unacquired) {
|
|
||||||
dispatch(onSelectDevice(unacquired));
|
|
||||||
} else {
|
|
||||||
const latest: Array<TrezorDevice> = sortDevices(devices);
|
|
||||||
const firstConnected: ?TrezorDevice = latest.find(d => d.connected);
|
|
||||||
dispatch(onSelectDevice(firstConnected || latest[0]));
|
|
||||||
|
|
||||||
// TODO
|
|
||||||
if (initialParams) {
|
|
||||||
if (!initialParams.hasOwnProperty('network') && initialPathname !== getState().router.location.pathname) {
|
|
||||||
// dispatch( push(initialPathname) );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
export const switchToFirstAvailableDevice = (): AsyncAction => async (dispatch: Dispatch, getState: GetState): Promise<void> => {
|
|
||||||
const { devices } = getState();
|
|
||||||
if (devices.length > 0) {
|
|
||||||
// TODO: Priority:
|
|
||||||
// 1. First Unacquired
|
|
||||||
// 2. First connected
|
|
||||||
// 3. Saved with latest timestamp
|
|
||||||
const unacquired = devices.find(d => !d.features);
|
|
||||||
if (unacquired) {
|
|
||||||
dispatch(initConnectedDevice(unacquired));
|
|
||||||
} else {
|
|
||||||
const latest: Array<TrezorDevice> = sortDevices(devices);
|
|
||||||
const firstConnected: ?TrezorDevice = latest.find(d => d.connected);
|
|
||||||
dispatch(onSelectDevice(firstConnected || latest[0]));
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
dispatch(push('/'));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
export const getSelectedDeviceState = (): AsyncAction => async (dispatch: Dispatch, getState: GetState): Promise<void> => {
|
export const getSelectedDeviceState = (): AsyncAction => async (dispatch: Dispatch, getState: GetState): Promise<void> => {
|
||||||
const selected = getState().wallet.selectedDevice;
|
const selected = getState().wallet.selectedDevice;
|
||||||
if (selected
|
if (selected
|
||||||
@ -391,13 +283,6 @@ export function acquire(): AsyncAction {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export const gotoDeviceSettings = (device: TrezorDevice): ThunkAction => (dispatch: Dispatch): void => {
|
|
||||||
if (device.features) {
|
|
||||||
const devUrl: string = `${device.features.device_id}${device.instance ? `:${device.instance}` : ''}`;
|
|
||||||
dispatch(push(`/device/${devUrl}/settings`));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
// called from Aside - device menu (forget single instance)
|
// called from Aside - device menu (forget single instance)
|
||||||
export const forget = (device: TrezorDevice): Action => ({
|
export const forget = (device: TrezorDevice): Action => ({
|
||||||
type: CONNECT.FORGET_REQUEST,
|
type: CONNECT.FORGET_REQUEST,
|
||||||
|
@ -1,42 +1,21 @@
|
|||||||
/* @flow */
|
/* @flow */
|
||||||
import { LOCATION_CHANGE/* , replace */ } from 'react-router-redux';
|
import { LOCATION_CHANGE, replace } from 'react-router-redux';
|
||||||
import * as CONNECT from 'actions/constants/TrezorConnect';
|
import * as CONNECT from 'actions/constants/TrezorConnect';
|
||||||
import * as WALLET from 'actions/constants/wallet';
|
import * as WALLET from 'actions/constants/wallet';
|
||||||
import * as NotificationActions from 'actions/NotificationActions';
|
import * as NotificationActions from 'actions/NotificationActions';
|
||||||
|
import * as RouterActions from 'actions/RouterActions';
|
||||||
|
|
||||||
import type {
|
import type {
|
||||||
Middleware,
|
Middleware,
|
||||||
MiddlewareAPI,
|
MiddlewareAPI,
|
||||||
MiddlewareDispatch,
|
MiddlewareDispatch,
|
||||||
Action,
|
Action,
|
||||||
|
ThunkAction,
|
||||||
RouterLocationState,
|
RouterLocationState,
|
||||||
TrezorDevice,
|
TrezorDevice,
|
||||||
} from 'flowtype';
|
} from 'flowtype';
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Middleware used for init application and managing router path.
|
|
||||||
*/
|
|
||||||
|
|
||||||
const pathToParams = (path: string): RouterLocationState => {
|
|
||||||
const urlParts: Array<string> = path.split('/').slice(1);
|
|
||||||
const params: RouterLocationState = {};
|
|
||||||
if (urlParts.length < 1 || path === '/') return params;
|
|
||||||
|
|
||||||
for (let i = 0, len = urlParts.length; i < len; i += 2) {
|
|
||||||
params[urlParts[i]] = urlParts[i + 1] || urlParts[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (params.hasOwnProperty('device')) {
|
|
||||||
const isClonedDevice: Array<string> = params.device.split(':');
|
|
||||||
if (isClonedDevice.length > 1) {
|
|
||||||
params.device = isClonedDevice[0];
|
|
||||||
params.deviceInstance = isClonedDevice[1];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return params;
|
|
||||||
};
|
|
||||||
|
|
||||||
const validation = (api: MiddlewareAPI, params: RouterLocationState): boolean => {
|
const validation = (api: MiddlewareAPI, params: RouterLocationState): boolean => {
|
||||||
if (params.hasOwnProperty('device')) {
|
if (params.hasOwnProperty('device')) {
|
||||||
const { devices } = api.getState();
|
const { devices } = api.getState();
|
||||||
@ -64,93 +43,148 @@ const validation = (api: MiddlewareAPI, params: RouterLocationState): boolean =>
|
|||||||
|
|
||||||
return true;
|
return true;
|
||||||
};
|
};
|
||||||
|
*/
|
||||||
|
|
||||||
let __unloading: boolean = false;
|
const deviceModeValidation = (api: MiddlewareAPI, current: RouterLocationState, requested: RouterLocationState): boolean => {
|
||||||
|
// allow url change if requested device is not the same as current state
|
||||||
|
if (current.device !== requested.device) return true;
|
||||||
|
// find device
|
||||||
|
const { devices } = api.getState();
|
||||||
|
let device: ?TrezorDevice;
|
||||||
|
if (requested.hasOwnProperty('deviceInstance')) {
|
||||||
|
device = devices.find(d => d.features && d.features.device_id === requested.device && d.instance === parseInt(requested.deviceInstance, 10));
|
||||||
|
} else {
|
||||||
|
device = devices.find(d => d.path === requested.device || (d.features && d.features.device_id === requested.device));
|
||||||
|
}
|
||||||
|
if (!device) return false;
|
||||||
|
if (!device.features) return false;
|
||||||
|
if (device.firmware === 'required') return false;
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Redux Middleware used for managing router path
|
||||||
|
* This middleware couldn't use async/await because LOCATION_CHANGE action is also synchronized with RouterReducer (react-router-redux)
|
||||||
|
*/
|
||||||
|
const RouterService1: Middleware = (api: MiddlewareAPI) => (next: MiddlewareDispatch) => (action: Action): Action => {
|
||||||
|
if (action.type !== LOCATION_CHANGE) {
|
||||||
|
return next(action);
|
||||||
|
}
|
||||||
|
|
||||||
|
action.payload.state = api.dispatch( RouterActions.pathToParams(action.payload.pathname) );
|
||||||
|
|
||||||
|
next(action);
|
||||||
|
|
||||||
|
return action;
|
||||||
|
}
|
||||||
|
|
||||||
const RouterService: Middleware = (api: MiddlewareAPI) => (next: MiddlewareDispatch) => (action: Action): Action => {
|
const RouterService: Middleware = (api: MiddlewareAPI) => (next: MiddlewareDispatch) => (action: Action): Action => {
|
||||||
if (action.type === WALLET.ON_BEFORE_UNLOAD) {
|
// make sure that middleware should process this action
|
||||||
__unloading = true;
|
if (action.type !== LOCATION_CHANGE || api.getState().wallet.unloading) {
|
||||||
} else if (action.type === LOCATION_CHANGE && !__unloading) {
|
// Pass action through by default
|
||||||
const { location } = api.getState().router;
|
return next(action);
|
||||||
|
}
|
||||||
|
|
||||||
|
const { location } = api.getState().router;
|
||||||
|
const requestedUrl: string = action.payload.pathname;
|
||||||
|
// map current and incoming url into RouterLocationState object
|
||||||
|
const currentParams = api.dispatch( RouterActions.pathToParams(location ? location.pathname : '/') );
|
||||||
|
const requestedParams = api.dispatch( RouterActions.pathToParams(requestedUrl) );
|
||||||
|
// postActions will be dispatched AFTER propagation of LOCATION_CHANGE action using next(action) below
|
||||||
|
const postActions: Array<Action | ThunkAction> = [];
|
||||||
|
const urlChanged: boolean = location ? requestedUrl !== location.pathname : true;
|
||||||
|
let redirectUrl: ?string;
|
||||||
|
|
||||||
|
if (!location) {
|
||||||
|
// handle first url change
|
||||||
|
// store requested url in WalletReducer and try to redirect back there if possible after application is ready
|
||||||
|
// TODO: validate if initial url is potentially correct
|
||||||
|
postActions.push({
|
||||||
|
type: WALLET.SET_INITIAL_URL,
|
||||||
|
pathname: action.payload.pathname,
|
||||||
|
state: requestedParams,
|
||||||
|
});
|
||||||
|
// temporary redirect to landing page (loading screen)
|
||||||
|
// and wait until application is ready
|
||||||
|
redirectUrl = '/';
|
||||||
|
} else {
|
||||||
const { devices } = api.getState();
|
const { devices } = api.getState();
|
||||||
|
const { ready } = api.getState().wallet;
|
||||||
const { error } = api.getState().connect;
|
const { error } = api.getState().connect;
|
||||||
|
const isModalOpened: boolean = api.getState().modal.opened;
|
||||||
|
// there are no connected devices or application isn't ready or initialization error occurred
|
||||||
|
const shouldDisplayLandingPage: boolean = devices.length < 1 || !ready || error !== null;
|
||||||
|
const isLandingPageUrl = api.dispatch( RouterActions.isLandingPageUrl(requestedUrl) );
|
||||||
|
const currentParamsAreValid: boolean = api.dispatch( RouterActions.paramsValidation(currentParams) );
|
||||||
|
|
||||||
const requestedParams: RouterLocationState = pathToParams(action.payload.pathname);
|
if (isModalOpened && urlChanged && currentParamsAreValid) {
|
||||||
const currentParams: RouterLocationState = pathToParams(location ? location.pathname : '/');
|
// Corner case: modal is opened and currentParams are still valid
|
||||||
const postActions: Array<Action> = [];
|
// example 1 (valid blocking): url changed while passphrase modal opened but device is still connected (we want user to finish this action)
|
||||||
|
|
||||||
let redirectPath: ?string;
|
|
||||||
// first event after application loads
|
|
||||||
if (!location) {
|
|
||||||
postActions.push({
|
|
||||||
type: WALLET.SET_INITIAL_URL,
|
|
||||||
pathname: action.payload.pathname,
|
|
||||||
state: requestedParams,
|
|
||||||
});
|
|
||||||
|
|
||||||
redirectPath = '/';
|
|
||||||
} else {
|
|
||||||
const isModalOpened: boolean = api.getState().modal.opened;
|
|
||||||
// there are no devices attached or initialization error occurs
|
|
||||||
const landingPage: boolean = devices.length < 1 || error !== null;
|
|
||||||
|
|
||||||
// modal is still opened and currentPath is still valid
|
|
||||||
// example 1 (valid blocking): url changes while passphrase modal opened but device is still connected (we want user to finish this action)
|
|
||||||
// example 2 (invalid blocking): url changes while passphrase modal opened because device disconnect
|
// example 2 (invalid blocking): url changes while passphrase modal opened because device disconnect
|
||||||
if (isModalOpened && action.payload.pathname !== location.pathname && validation(api, currentParams)) {
|
redirectUrl = location.pathname;
|
||||||
redirectPath = location.pathname;
|
console.warn('Modal still opened');
|
||||||
console.warn('Modal still opened');
|
} else if (shouldDisplayLandingPage) {
|
||||||
} else if (landingPage) {
|
if (!isLandingPageUrl) {
|
||||||
// keep route on landing page
|
// keep route on landing page
|
||||||
if (action.payload.pathname !== '/' && action.payload.pathname !== '/bridge') {
|
redirectUrl = '/';
|
||||||
redirectPath = '/';
|
}
|
||||||
}
|
} else {
|
||||||
} else {
|
// Process regular url change during application live cycle
|
||||||
// PATH VALIDATION
|
const requestedParamsAreValid: boolean = api.dispatch( RouterActions.paramsValidation(requestedParams) );
|
||||||
// redirect from root view
|
if (isLandingPageUrl) {
|
||||||
if (action.payload.pathname === '/' || !validation(api, requestedParams)) {
|
// Corner case: disallow displaying landing page
|
||||||
// TODO redirect to first device
|
// redirect to previous url
|
||||||
redirectPath = '/device/x';
|
// TODO: && currentParamsAreValid
|
||||||
} else if (requestedParams.device) {
|
redirectUrl = location.pathname;
|
||||||
if (requestedParams.network !== currentParams.network) {
|
} else if (!requestedParamsAreValid) {
|
||||||
postActions.push({
|
// Corner case: requested params are not valid
|
||||||
type: CONNECT.COIN_CHANGED,
|
// Neither device or network doesn't exists
|
||||||
payload: {
|
postActions.push( RouterActions.selectFirstAvailableDevice() );
|
||||||
network: requestedParams.network,
|
} else if (requestedParams.device) {
|
||||||
},
|
if (!deviceModeValidation(api, currentParams, requestedParams)) {
|
||||||
});
|
redirectUrl = location.pathname;
|
||||||
}
|
console.warn('Device is not in valid mode');
|
||||||
|
} else if (requestedParams.network !== currentParams.network) {
|
||||||
|
postActions.push({
|
||||||
|
type: CONNECT.COIN_CHANGED,
|
||||||
|
payload: {
|
||||||
|
network: requestedParams.network,
|
||||||
|
},
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (redirectPath) {
|
|
||||||
console.warn('Redirecting...', redirectPath);
|
|
||||||
// override action to keep routerReducer sync
|
|
||||||
const url: string = redirectPath;
|
|
||||||
action.payload.state = pathToParams(url);
|
|
||||||
action.payload.pathname = url;
|
|
||||||
// change url
|
|
||||||
// api.dispatch(replace(url));
|
|
||||||
} else {
|
|
||||||
action.payload.state = requestedParams;
|
|
||||||
}
|
|
||||||
|
|
||||||
// resolve LOCATION_CHANGE action
|
|
||||||
next(action);
|
|
||||||
|
|
||||||
// resolve post actions
|
|
||||||
postActions.forEach((a) => {
|
|
||||||
api.dispatch(a);
|
|
||||||
});
|
|
||||||
|
|
||||||
api.dispatch(NotificationActions.clear(currentParams, requestedParams));
|
|
||||||
|
|
||||||
return action;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Pass all actions through by default
|
if (redirectUrl) {
|
||||||
return next(action);
|
const url: string = redirectUrl;
|
||||||
|
// override action to keep RouterReducer synchronized
|
||||||
|
action.payload.state = api.dispatch( RouterActions.pathToParams(url) );
|
||||||
|
// change url
|
||||||
|
if (requestedUrl !== url) {
|
||||||
|
console.warn('Redirecting from', requestedUrl, 'to', url);
|
||||||
|
action.payload.pathname = url;
|
||||||
|
postActions.unshift( replace(url) )
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// override action to keep RouterReducer synchronized
|
||||||
|
action.payload.state = requestedParams;
|
||||||
|
}
|
||||||
|
|
||||||
|
// resolve LOCATION_CHANGE action
|
||||||
|
next(action);
|
||||||
|
|
||||||
|
// resolve all post actions
|
||||||
|
postActions.forEach((a) => {
|
||||||
|
api.dispatch(a);
|
||||||
|
});
|
||||||
|
|
||||||
|
// TODO: move this to wallet service?
|
||||||
|
api.dispatch(NotificationActions.clear(currentParams, requestedParams));
|
||||||
|
|
||||||
|
return action;
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export default RouterService;
|
export default RouterService;
|
@ -1,5 +1,4 @@
|
|||||||
/* @flow */
|
/* @flow */
|
||||||
import { push } from 'react-router-redux';
|
|
||||||
|
|
||||||
import TrezorConnect, {
|
import TrezorConnect, {
|
||||||
TRANSPORT, DEVICE_EVENT, UI_EVENT, UI, DEVICE, BLOCKCHAIN
|
TRANSPORT, DEVICE_EVENT, UI_EVENT, UI, DEVICE, BLOCKCHAIN
|
||||||
@ -7,6 +6,7 @@ import TrezorConnect, {
|
|||||||
import * as TrezorConnectActions from 'actions/TrezorConnectActions';
|
import * as TrezorConnectActions from 'actions/TrezorConnectActions';
|
||||||
import * as DiscoveryActions from 'actions/DiscoveryActions';
|
import * as DiscoveryActions from 'actions/DiscoveryActions';
|
||||||
import * as BlockchainActions from 'actions/BlockchainActions';
|
import * as BlockchainActions from 'actions/BlockchainActions';
|
||||||
|
import * as RouterActions from 'actions/RouterActions';
|
||||||
import * as ModalActions from 'actions/ModalActions';
|
import * as ModalActions from 'actions/ModalActions';
|
||||||
import * as STORAGE from 'actions/constants/localStorage';
|
import * as STORAGE from 'actions/constants/localStorage';
|
||||||
import * as CONNECT from 'actions/constants/TrezorConnect';
|
import * as CONNECT from 'actions/constants/TrezorConnect';
|
||||||
@ -31,7 +31,7 @@ const TrezorConnectService: Middleware = (api: MiddlewareAPI) => (next: Middlewa
|
|||||||
api.dispatch(TrezorConnectActions.init());
|
api.dispatch(TrezorConnectActions.init());
|
||||||
} else if (action.type === TRANSPORT.ERROR) {
|
} else if (action.type === TRANSPORT.ERROR) {
|
||||||
// TODO: check if modal is open
|
// TODO: check if modal is open
|
||||||
// api.dispatch( push('/') );
|
// api.dispatch( RouterActions.gotoLandingPage() );
|
||||||
} else if (action.type === TRANSPORT.START) {
|
} else if (action.type === TRANSPORT.START) {
|
||||||
api.dispatch(BlockchainActions.init());
|
api.dispatch(BlockchainActions.init());
|
||||||
} else if (action.type === BLOCKCHAIN_READY) {
|
} else if (action.type === BLOCKCHAIN_READY) {
|
||||||
@ -42,7 +42,7 @@ const TrezorConnectService: Middleware = (api: MiddlewareAPI) => (next: Middlewa
|
|||||||
api.dispatch(ModalActions.onRememberRequest(prevModalState));
|
api.dispatch(ModalActions.onRememberRequest(prevModalState));
|
||||||
} else if (action.type === CONNECT.FORGET) {
|
} else if (action.type === CONNECT.FORGET) {
|
||||||
//api.dispatch( TrezorConnectActions.forgetDevice(action.device) );
|
//api.dispatch( TrezorConnectActions.forgetDevice(action.device) );
|
||||||
api.dispatch(TrezorConnectActions.switchToFirstAvailableDevice());
|
api.dispatch( RouterActions.selectFirstAvailableDevice() );
|
||||||
} else if (action.type === CONNECT.FORGET_SINGLE) {
|
} else if (action.type === CONNECT.FORGET_SINGLE) {
|
||||||
if (api.getState().devices.length < 1 && action.device.connected) {
|
if (api.getState().devices.length < 1 && action.device.connected) {
|
||||||
// prompt disconnect device info in LandingPage
|
// prompt disconnect device info in LandingPage
|
||||||
@ -50,9 +50,9 @@ const TrezorConnectService: Middleware = (api: MiddlewareAPI) => (next: Middlewa
|
|||||||
type: CONNECT.DISCONNECT_REQUEST,
|
type: CONNECT.DISCONNECT_REQUEST,
|
||||||
device: action.device,
|
device: action.device,
|
||||||
});
|
});
|
||||||
api.dispatch(push('/'));
|
api.dispatch( RouterActions.gotoLandingPage() );
|
||||||
} else {
|
} else {
|
||||||
api.dispatch(TrezorConnectActions.switchToFirstAvailableDevice());
|
api.dispatch( RouterActions.selectFirstAvailableDevice() );
|
||||||
}
|
}
|
||||||
} else if (action.type === DEVICE.CONNECT || action.type === DEVICE.CONNECT_UNACQUIRED) {
|
} else if (action.type === DEVICE.CONNECT || action.type === DEVICE.CONNECT_UNACQUIRED) {
|
||||||
api.dispatch(DiscoveryActions.restore());
|
api.dispatch(DiscoveryActions.restore());
|
||||||
@ -60,7 +60,7 @@ const TrezorConnectService: Middleware = (api: MiddlewareAPI) => (next: Middlewa
|
|||||||
} else if (action.type === CONNECT.AUTH_DEVICE) {
|
} else if (action.type === CONNECT.AUTH_DEVICE) {
|
||||||
api.dispatch(DiscoveryActions.check());
|
api.dispatch(DiscoveryActions.check());
|
||||||
} else if (action.type === CONNECT.DUPLICATE) {
|
} else if (action.type === CONNECT.DUPLICATE) {
|
||||||
api.dispatch(TrezorConnectActions.onSelectDevice(action.device));
|
api.dispatch(RouterActions.selectDevice(action.device));
|
||||||
} else if (action.type === CONNECT.COIN_CHANGED) {
|
} else if (action.type === CONNECT.COIN_CHANGED) {
|
||||||
api.dispatch(TrezorConnectActions.coinChanged(action.payload.network));
|
api.dispatch(TrezorConnectActions.coinChanged(action.payload.network));
|
||||||
} else if (action.type === BLOCKCHAIN.BLOCK) {
|
} else if (action.type === BLOCKCHAIN.BLOCK) {
|
||||||
|
@ -6,6 +6,7 @@ import { LOCATION_CHANGE } from 'react-router-redux';
|
|||||||
import * as WALLET from 'actions/constants/wallet';
|
import * as WALLET from 'actions/constants/wallet';
|
||||||
|
|
||||||
import * as WalletActions from 'actions/WalletActions';
|
import * as WalletActions from 'actions/WalletActions';
|
||||||
|
import * as RouterActions from 'actions/RouterActions';
|
||||||
import * as LocalStorageActions from 'actions/LocalStorageActions';
|
import * as LocalStorageActions from 'actions/LocalStorageActions';
|
||||||
import * as TrezorConnectActions from 'actions/TrezorConnectActions';
|
import * as TrezorConnectActions from 'actions/TrezorConnectActions';
|
||||||
import * as SelectedAccountActions from 'actions/SelectedAccountActions';
|
import * as SelectedAccountActions from 'actions/SelectedAccountActions';
|
||||||
@ -29,11 +30,14 @@ const WalletService: Middleware = (api: MiddlewareAPI) => (next: MiddlewareDispa
|
|||||||
const { location } = api.getState().router;
|
const { location } = api.getState().router;
|
||||||
if (!location) {
|
if (!location) {
|
||||||
api.dispatch(WalletActions.init());
|
api.dispatch(WalletActions.init());
|
||||||
// load data from config.json and local storage
|
|
||||||
api.dispatch(LocalStorageActions.loadData());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (action.type === WALLET.SET_INITIAL_URL) {
|
||||||
|
// load data from config.json and local storage
|
||||||
|
api.dispatch(LocalStorageActions.loadData());
|
||||||
|
}
|
||||||
|
|
||||||
// pass action
|
// pass action
|
||||||
next(action);
|
next(action);
|
||||||
|
|
||||||
@ -41,18 +45,23 @@ const WalletService: Middleware = (api: MiddlewareAPI) => (next: MiddlewareDispa
|
|||||||
api.dispatch(WalletActions.clearUnavailableDevicesData(prevState, action.device));
|
api.dispatch(WalletActions.clearUnavailableDevicesData(prevState, action.device));
|
||||||
}
|
}
|
||||||
|
|
||||||
// update common values in WallerReducer
|
// update common values ONLY if application is ready
|
||||||
api.dispatch(WalletActions.updateSelectedValues(prevState, action));
|
if (api.getState().wallet.ready) {
|
||||||
|
// update common values in WallerReducer
|
||||||
|
api.dispatch(WalletActions.updateSelectedValues(prevState, action));
|
||||||
|
|
||||||
// update common values in SelectedAccountReducer
|
// update common values in SelectedAccountReducer
|
||||||
api.dispatch(SelectedAccountActions.updateSelectedValues(prevState, action));
|
api.dispatch(SelectedAccountActions.updateSelectedValues(prevState, action));
|
||||||
|
}
|
||||||
|
|
||||||
// selected device changed
|
// handle selected device change
|
||||||
if (action.type === WALLET.SET_SELECTED_DEVICE) {
|
if (action.type === WALLET.SET_SELECTED_DEVICE) {
|
||||||
if (action.device) {
|
if (action.device) {
|
||||||
|
// try to authorize device
|
||||||
api.dispatch(TrezorConnectActions.getSelectedDeviceState());
|
api.dispatch(TrezorConnectActions.getSelectedDeviceState());
|
||||||
} else {
|
} else {
|
||||||
api.dispatch(TrezorConnectActions.switchToFirstAvailableDevice());
|
// try select different device
|
||||||
|
api.dispatch(RouterActions.selectFirstAvailableDevice());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user