From aae479248c6b628df58ce7229de407e86d1f5413 Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Mon, 30 Jul 2018 09:57:27 +0200 Subject: [PATCH 01/12] Update to latest trezor-connect --- yarn.lock | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/yarn.lock b/yarn.lock index a2694ede..b411cf5d 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3361,7 +3361,7 @@ eventemitter3@^3.0.0: version "3.1.0" resolved "https://registry.yarnpkg.com/eventemitter3/-/eventemitter3-3.1.0.tgz#090b4d6cdbd645ed10bf750d4b5407942d7ba163" -events@^1.0.0: +events@^1.0.0, events@^1.1.1: version "1.1.1" resolved "https://registry.yarnpkg.com/events/-/events-1.1.1.tgz#9ebdb7635ad099c70dcc4c2a1f5004288e8bd924" From ce00abd8387a2bedff439e2268763e9bfcb35b6c Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Mon, 30 Jul 2018 11:28:19 +0200 Subject: [PATCH 02/12] Remove 'connectSrc' from TrezorConnect.init() settings - connect to a public connect server --- src/js/actions/TrezorConnectActions.js | 45 +++++++++++++++++--------- 1 file changed, 30 insertions(+), 15 deletions(-) diff --git a/src/js/actions/TrezorConnectActions.js b/src/js/actions/TrezorConnectActions.js index 72278921..cf21d343 100644 --- a/src/js/actions/TrezorConnectActions.js +++ b/src/js/actions/TrezorConnectActions.js @@ -112,21 +112,20 @@ export const init = (): AsyncAction => async (dispatch: Dispatch, getState: GetS }); }); - try { - await TrezorConnect.init({ - transportReconnect: true, - // connectSrc: 'https://localhost:8088/', - connectSrc: 'https://sisyfos.trezor.io/', - debug: false, - popup: false, - webusb: true, - pendingTransportEvent: (getState().devices.length < 1), - }); - } catch (error) { - // dispatch({ - // type: CONNECT.INITIALIZATION_ERROR, - // error - // }) + try { + await TrezorConnect.init({ + transportReconnect: true, + debug: false, + popup: false, + webusb: true, + pendingTransportEvent: (getState().devices.length < 1) + }); + } catch (error) { + // dispatch({ + // type: CONNECT.INITIALIZATION_ERROR, + // error + // }) + } } }; @@ -170,6 +169,22 @@ export const postInit = (): ThunkAction => (dispatch: Dispatch, getState: GetSta // dispatch( push(initialPathname) ); } else { + if (devices.length > 0) { + const unacquired: ?TrezorDevice = devices.find(d => d.unacquired); + if (unacquired) { + dispatch( onSelectDevice(unacquired) ); + } else { + const latest: Array = 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) ); + } else { + + } } } } From bcea824a9092ec972472083a0ffebfd3d735a966 Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Mon, 30 Jul 2018 12:57:02 +0200 Subject: [PATCH 03/12] Update parametr object when calling 'TrezorConnect.ethereumSignTransaction' - to match a corresponding Flowtype --- src/js/actions/SendFormActions.js | 23 +++++++++++++++++++++-- 1 file changed, 21 insertions(+), 2 deletions(-) diff --git a/src/js/actions/SendFormActions.js b/src/js/actions/SendFormActions.js index e1e6a5e7..423d96f6 100644 --- a/src/js/actions/SendFormActions.js +++ b/src/js/actions/SendFormActions.js @@ -830,6 +830,25 @@ export const onSend = (): AsyncAction => async (dispatch: Dispatch, getState: Ge if (!selected) return; const signedTransaction = await TrezorConnect.ethereumSignTransaction({ + device: { + path: selected.path, + instance: selected.instance, + state: selected.state + }, + useEmptyPassphrase: !selected.instance, + path: txData.address_n, + transaction: { + to: strip(txData.to), + value: strip(txData.value), + gasPrice: strip(txData.gasPrice), + gasLimit: strip(txData.gasLimit), + nonce: strip(txData.nonce), + data: strip(txData.data), + chainId: txData.chainId, + r: txData.r, + s: txData.s, + v: txData.v, + }, device: { path: selected.path, instance: selected.instance, @@ -860,8 +879,8 @@ export const onSend = (): AsyncAction => async (dispatch: Dispatch, getState: Ge return; } - txData.r = `0x${signedTransaction.payload.r}`; - txData.s = `0x${signedTransaction.payload.s}`; + txData.r = signedTransaction.payload.r; + txData.s = signedTransaction.payload.s; txData.v = w3.toHex(signedTransaction.payload.v); From 3082c7fdd7ef33ce92fae3615a6998f2c51dca5c Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Mon, 30 Jul 2018 13:00:00 +0200 Subject: [PATCH 04/12] Remove unnecessary import --- src/js/actions/TrezorConnectActions.js | 1 - 1 file changed, 1 deletion(-) diff --git a/src/js/actions/TrezorConnectActions.js b/src/js/actions/TrezorConnectActions.js index cf21d343..da85b6be 100644 --- a/src/js/actions/TrezorConnectActions.js +++ b/src/js/actions/TrezorConnectActions.js @@ -16,7 +16,6 @@ import { resolveAfter } from '../utils/promiseUtils'; import type { Device, - ResponseMessage, DeviceMessage, UiMessage, TransportMessage, From 28285754e285a075fe68eca44c248b7564525c62 Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Mon, 30 Jul 2018 13:02:02 +0200 Subject: [PATCH 05/12] Check wheter 'device.features' are defined --- src/js/actions/TrezorConnectActions.js | 15 ++++++++------- src/js/actions/WalletActions.js | 4 +++- src/js/reducers/DevicesReducer.js | 4 ++-- 3 files changed, 13 insertions(+), 10 deletions(-) diff --git a/src/js/actions/TrezorConnectActions.js b/src/js/actions/TrezorConnectActions.js index da85b6be..28c35b8d 100644 --- a/src/js/actions/TrezorConnectActions.js +++ b/src/js/actions/TrezorConnectActions.js @@ -330,13 +330,14 @@ export const deviceDisconnect = (device: Device): AsyncAction => async (dispatch dispatch(DiscoveryActions.stop(selected)); } - const instances = getState().devices.filter(d => d.features && d.state && !d.remember && d.features.device_id === device.features.device_id); - if (instances.length > 0) { - dispatch({ - type: CONNECT.REMEMBER_REQUEST, - device: instances[0], - instances, - }); + const instances = getState().devices.filter(d => d.features && d.state && !d.remember && device.features && d.features.device_id === device.features.device_id); + if (instances.length > 0) { + dispatch({ + type: CONNECT.REMEMBER_REQUEST, + device: instances[0], + instances, + }); + } } } }; diff --git a/src/js/actions/WalletActions.js b/src/js/actions/WalletActions.js index 763bb8db..09fcc423 100644 --- a/src/js/actions/WalletActions.js +++ b/src/js/actions/WalletActions.js @@ -75,7 +75,9 @@ export const toggleDeviceDropdown = (opened: boolean): WalletAction => ({ export const clearUnavailableDevicesData = (prevState: State, device: Device): ThunkAction => (dispatch: Dispatch, getState: GetState): void => { if (!device.features) return; - const affectedDevices = prevState.devices.filter(d => d.features + const affectedDevices = prevState.devices.filter(d => + d.features + && device.features && d.features.device_id === device.features.device_id && d.features.passphrase_protection !== device.features.passphrase_protection); diff --git a/src/js/reducers/DevicesReducer.js b/src/js/reducers/DevicesReducer.js index 7bc64155..6248b412 100644 --- a/src/js/reducers/DevicesReducer.js +++ b/src/js/reducers/DevicesReducer.js @@ -112,7 +112,7 @@ const addDevice = (state: State, device: Device): State => { // changedDevices.push(newDevice); // } - const changedDevices: Array = affectedDevices.filter(d => d.features && d.features.passphrase_protection === device.features.passphrase_protection).map(d => mergeDevices(d, { ...device, connected: true, available: true })); + const changedDevices: Array = affectedDevices.filter(d => d.features && device.features && d.features.passphrase_protection === device.features.passphrase_protection).map(d => mergeDevices(d, { ...device, connected: true, available: true })); if (changedDevices.length !== affectedDevices.length) { changedDevices.push(newDevice); } @@ -150,7 +150,7 @@ const changeDevice = (state: State, device: Device): State => { // find devices with the same device_id and passphrase_protection settings // or devices with the same path (TODO: should be that way?) - const affectedDevices: Array = state.filter(d => (d.features && d.features.device_id === device.features.device_id && d.features.passphrase_protection === device.features.passphrase_protection) + const affectedDevices: Array = state.filter(d => (d.features && device.features && d.features.device_id === device.features.device_id && d.features.passphrase_protection === device.features.passphrase_protection) || (d.features && d.path.length > 0 && d.path === device.path)); const otherDevices: Array = state.filter(d => affectedDevices.indexOf(d) === -1); From 61d902b5c79f1b2c32e66412b9792ae6e1b22b3a Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Mon, 30 Jul 2018 13:02:45 +0200 Subject: [PATCH 06/12] Remove case for 'DEVICE.DISCONNECT_UNACQUIRED' - this event doesn't exist now --- src/js/reducers/DevicesReducer.js | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/js/reducers/DevicesReducer.js b/src/js/reducers/DevicesReducer.js index 6248b412..a3d0f672 100644 --- a/src/js/reducers/DevicesReducer.js +++ b/src/js/reducers/DevicesReducer.js @@ -65,7 +65,7 @@ const addDevice = (state: State, device: Device): State => { } otherDevices = state.filter(d => affectedDevices.indexOf(d) === -1); } else { - affectedDevices = state.filter(d => d.features && d.features.device_id === device.features.device_id); + affectedDevices = state.filter(d => d.features && device.features && d.features.device_id === device.features.device_id); const unacquiredDevices = state.filter(d => d.path.length > 0 && d.path === device.path); otherDevices = state.filter(d => affectedDevices.indexOf(d) < 0 && unacquiredDevices.indexOf(d) < 0); } @@ -251,10 +251,9 @@ export default function devices(state: State = initialState, action: Action): St case DEVICE.CHANGED: return changeDevice(state, { ...action.device, connected: true, available: true }); - // TODO: check if available will propagate to unavailable + // TODO: check if available will propagate to unavailable case DEVICE.DISCONNECT: - case DEVICE.DISCONNECT_UNACQUIRED: return disconnectDevice(state, action.device); case WALLET.SET_SELECTED_DEVICE: From 43079780696a3263ef6ed19601e22c54212ba7b9 Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Mon, 30 Jul 2018 13:44:53 +0200 Subject: [PATCH 07/12] Use 'device.status' instead of 'device.isUsedElsewhere' --- src/js/reducers/ModalReducer.js | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/js/reducers/ModalReducer.js b/src/js/reducers/ModalReducer.js index e545d561..996e6215 100644 --- a/src/js/reducers/ModalReducer.js +++ b/src/js/reducers/ModalReducer.js @@ -53,10 +53,11 @@ export default function modal(state: State = initialState, action: Action): Stat windowType: action.type, }; - case DEVICE.CHANGED: - if (state.opened && action.device.path === state.device.path && action.device.isUsedElsewhere) { - return initialState; + case DEVICE.CHANGED : + if (state.opened && action.device.path === state.device.path && action.device.status === 'occupied') { + return initialState } + return state; case DEVICE.DISCONNECT: From 250141236b6457657d06cc4db592abd9675f84cb Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Thu, 2 Aug 2018 11:44:52 +0200 Subject: [PATCH 08/12] Update TrezorDevice's `isUsedElsewhere` & `unacquired` properties - both properties are now deprecated - following properties are now used instead (matching trezor-connect): - `type` with possible values `acquired` | `unacquired` | `unreadable` - `status` with possible values `available` | `occupied` | `used` --- src/flowtype/index.js | 8 +++++--- src/js/actions/TrezorConnectActions.js | 4 ++-- src/js/components/wallet/aside/DeviceSelection.js | 8 ++++---- src/js/reducers/DevicesReducer.js | 11 ++++++----- src/js/reducers/utils/index.js | 2 +- 5 files changed, 18 insertions(+), 15 deletions(-) diff --git a/src/flowtype/index.js b/src/flowtype/index.js index a66b4135..7de58c39 100644 --- a/src/flowtype/index.js +++ b/src/flowtype/index.js @@ -53,11 +53,13 @@ export type TrezorDevice = { instanceLabel: string; instanceName: ?string; features?: Features; - unacquired?: boolean; - isUsedElsewhere?: boolean; + // unacquired?: boolean; // device.type === 'unacquired' && device.type !== 'unreadable' + // isUsedElsewhere?: boolean; // device.status === 'occupied' + type: 'acquired' | 'unacquired' | 'unreadable'; + status: 'available' | 'occupied' | 'used'; featuresNeedsReload?: boolean; ts: number; -} +}; export type RouterLocationState = LocationState; diff --git a/src/js/actions/TrezorConnectActions.js b/src/js/actions/TrezorConnectActions.js index 28c35b8d..eb7c64b6 100644 --- a/src/js/actions/TrezorConnectActions.js +++ b/src/js/actions/TrezorConnectActions.js @@ -169,7 +169,7 @@ export const postInit = (): ThunkAction => (dispatch: Dispatch, getState: GetSta } else { if (devices.length > 0) { - const unacquired: ?TrezorDevice = devices.find(d => d.unacquired); + const unacquired: ?TrezorDevice = devices.find(d => d.type === 'unacquired'); if (unacquired) { dispatch( onSelectDevice(unacquired) ); } else { @@ -260,7 +260,7 @@ export const switchToFirstAvailableDevice = (): AsyncAction => async (dispatch: // 1. First Unacquired // 2. First connected // 3. Saved with latest timestamp - const unacquired = devices.find(d => d.unacquired); + const unacquired = devices.find(d => d.type === 'unacquired'); if (unacquired) { dispatch(initConnectedDevice(unacquired)); } else { diff --git a/src/js/components/wallet/aside/DeviceSelection.js b/src/js/components/wallet/aside/DeviceSelection.js index 443e37dc..eeae1b90 100644 --- a/src/js/components/wallet/aside/DeviceSelection.js +++ b/src/js/components/wallet/aside/DeviceSelection.js @@ -26,11 +26,11 @@ export const DeviceSelect = (props: Props) => { css += ' unavailable'; deviceStatus = 'Unavailable'; } else { - if (selected.unacquired) { + if (selected.type === 'unacquired') { css += ' unacquired'; deviceStatus = 'Used in other window'; } - if (selected.isUsedElsewhere) { + if (selected.status === 'occupied') { css += ' used-elsewhere'; deviceStatus = 'Used in other window'; } else if (selected.featuresNeedsReload) { @@ -147,7 +147,7 @@ export class DeviceDropdown extends Component { if (selected.features) { const deviceMenuItems: Array = []; - if (selected.isUsedElsewhere) { + if (selected.status === 'occupied') { deviceMenuItems.push({ type: 'reload', label: 'Renew session' }); } else if (selected.featuresNeedsReload) { deviceMenuItems.push({ type: 'reload', label: 'Renew session' }); @@ -177,7 +177,7 @@ export class DeviceDropdown extends Component { let deviceStatus: string = 'Connected'; let css: string = 'device item'; - if (dev.unacquired || dev.isUsedElsewhere) { + if (dev.type === 'unacquired' || dev.status === 'occupied') { deviceStatus = 'Used in other window'; css += ' unacquired'; } else if (!dev.connected) { diff --git a/src/js/reducers/DevicesReducer.js b/src/js/reducers/DevicesReducer.js index a3d0f672..d96ffc67 100644 --- a/src/js/reducers/DevicesReducer.js +++ b/src/js/reducers/DevicesReducer.js @@ -44,8 +44,8 @@ const mergeDevices = (current: TrezorDevice, upcoming: Device | TrezorDevice): T }; // corner-case: trying to merge unacquired device with acquired // make sure that sensitive fields will not be changed and device will remain acquired - if (upcoming.unacquired && current.state) { - dev.unacquired = false; + if (upcoming.type === 'unacquired' && current.state) { + dev.type = 'unacquired'; dev.features = current.features; dev.label = current.label; } @@ -184,7 +184,8 @@ const devicesFromStorage = (devices: Array): State => devices.map( path: '', acquiring: false, featuresNeedsReload: false, - isUsedElsewhere: false, + //isUsedElsewhere: false, + status: 'available', })); // Remove all device reference from State @@ -204,11 +205,11 @@ const disconnectDevice = (state: State, device: Device): State => { const otherDevices: State = state.filter(d => affectedDevices.indexOf(d) === -1); if (affectedDevices.length > 0) { - const acquiredDevices = affectedDevices.filter(d => !d.unacquired && d.state); + const acquiredDevices = affectedDevices.filter(d => d.type !== 'unacquired' && d.type !== 'unreadable' && d.state); return otherDevices.concat(acquiredDevices.map((d) => { d.connected = false; d.available = false; - d.isUsedElsewhere = false; + d.status = 'used'; d.featuresNeedsReload = false; d.path = ''; return d; diff --git a/src/js/reducers/utils/index.js b/src/js/reducers/utils/index.js index 26fb3761..11b5020d 100644 --- a/src/js/reducers/utils/index.js +++ b/src/js/reducers/utils/index.js @@ -30,7 +30,7 @@ export const getSelectedDevice = (state: State): ?TrezorDevice => { const instance: ?number = locationState.deviceInstance ? parseInt(locationState.deviceInstance) : undefined; return state.devices.find((d) => { - if (d.unacquired && d.path === locationState.device) { + if (d.type === 'unacquired' && d.path === locationState.device) { return true; } if (d.features && d.features.bootloader_mode && d.path === locationState.device) { return true; From cd4d7ed6b1cb1af09d81a78b95715c2ec33c98c4 Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Thu, 2 Aug 2018 15:19:26 +0200 Subject: [PATCH 09/12] Show loader after 'Acquire Device' button is clicked and is waiting for acquire --- src/js/components/common/LoaderCircle.js | 16 +++++++--- src/js/components/common/Notification.js | 10 +++++- src/js/components/wallet/pages/Acquire.js | 30 +++++++++++++----- src/styles/loader.less | 37 ++++++++++++++++------- src/styles/notification.less | 4 +-- 5 files changed, 72 insertions(+), 25 deletions(-) diff --git a/src/js/components/common/LoaderCircle.js b/src/js/components/common/LoaderCircle.js index fe4f4827..6020083a 100644 --- a/src/js/components/common/LoaderCircle.js +++ b/src/js/components/common/LoaderCircle.js @@ -3,14 +3,22 @@ import React from 'react'; -export default (props: { size: string, label?: string }): React$Element => { +type Props = { + size: string, + label?: string, + className?: string, +}; + +export default (props: Props): React$Element => { + const className = props.className ? `loader-circle ${props.className}` : 'loader-circle'; + const style = { width: `${props.size}px`, height: `${props.size}px`, - }; + } return ( -
+

{ props.label }

@@ -18,4 +26,4 @@ export default (props: { size: string, label?: string }): React$Element
); -}; \ No newline at end of file +}; diff --git a/src/js/components/common/Notification.js b/src/js/components/common/Notification.js index 59e450fa..ac80f222 100644 --- a/src/js/components/common/Notification.js +++ b/src/js/components/common/Notification.js @@ -5,6 +5,8 @@ import React from 'react'; import { bindActionCreators } from 'redux'; import { connect } from 'react-redux'; +import Loader from '../common/LoaderCircle'; + import * as NOTIFICATION from '~/js/actions/constants/notification'; import * as NotificationActions from '~/js/actions/NotificationActions'; import type { Action, State, Dispatch } from '~/flowtype'; @@ -21,7 +23,8 @@ type NProps = { title: string; message?: string; actions?: Array; - close?: typeof NotificationActions.close + close?: typeof NotificationActions.close, + loading?: boolean; } export const Notification = (props: NProps): React$Element => { @@ -48,6 +51,11 @@ export const Notification = (props: NProps): React$Element => { { actionButtons }
) : null } + { props.loading ? ( + + ) : null } ); diff --git a/src/js/components/wallet/pages/Acquire.js b/src/js/components/wallet/pages/Acquire.js index 1a3b768a..e60fa57e 100644 --- a/src/js/components/wallet/pages/Acquire.js +++ b/src/js/components/wallet/pages/Acquire.js @@ -23,16 +23,32 @@ const Acquire = (props: Props) => { }, }, ]; + const acquireDeviceAction = { + label: 'Acquire device', + callback: () => { + props.acquireDevice() + } + }; return (
- + {props.acquiring ? ( + + ) : ( + + )}
); }; diff --git a/src/styles/loader.less b/src/styles/loader.less index 6b5338ae..671e50d0 100644 --- a/src/styles/loader.less +++ b/src/styles/loader.less @@ -15,18 +15,18 @@ } .circular { - + width: 100%; height: 100%; animation: rotate 2s linear infinite; transform-origin: center center; - + position: absolute; - + .route { stroke: @color_gray_light; } - + .path { stroke-dasharray: 1, 200; stroke-dashoffset: 0; @@ -34,15 +34,15 @@ stroke-linecap: round; } } -} -@keyframes rotate { - 100% { - transform: rotate(360deg); + &.info { + .path { + animation: dash 1.5s ease-in-out infinite, colorInfo 6s ease-in-out infinite; + } } } -@keyframes dash { +@keyframes dash { 0% { stroke-dasharray: 1, 200; stroke-dashoffset: 0; @@ -57,7 +57,7 @@ } } -@keyframes color { +@keyframes color { 100%, 0% { stroke: @color_green_primary; } @@ -70,4 +70,19 @@ 80%, 90% { stroke: @color_green_tertiary; } -} \ No newline at end of file +} + +@keyframes colorInfo { + 100%, 0% { + stroke: @color_info_primary; + } + 40% { + stroke: @color_info_primary; + } + 66% { + stroke: @color_info_primary; + } + 80%, 90% { + stroke: @color_info_primary; + } +} diff --git a/src/styles/notification.less b/src/styles/notification.less index dc8aab70..d091ceab 100644 --- a/src/styles/notification.less +++ b/src/styles/notification.less @@ -40,7 +40,7 @@ h2 { font-size: 14px; font-weight: bold; - + padding: 0px; &:before { .icomoon-info; @@ -68,7 +68,7 @@ } } - + &.success { color: @color_success_primary; From 12f64bac19ea103e44f6344b7ff4b81b298ac4ce Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Mon, 6 Aug 2018 10:43:20 +0200 Subject: [PATCH 10/12] Add a webpack config to run with local Trezor Connect --- package.json | 1 + src/js/actions/TrezorConnectActions.js | 7 +- webpack/config.dev.local.babel.js | 164 +++++++++++++++++++++++++ webpack/constants.js | 10 +- 4 files changed, 180 insertions(+), 2 deletions(-) create mode 100644 webpack/config.dev.local.babel.js diff --git a/package.json b/package.json index 12fdc04e..125774f9 100644 --- a/package.json +++ b/package.json @@ -16,6 +16,7 @@ "license": "LGPL-3.0+", "scripts": { "dev": "webpack-dev-server --config ./webpack/config.dev.babel.js --mode development", + "dev:local": "webpack-dev-server --config ./webpack/config.dev.local.babel.js --mode development", "build": "rm -rf build && webpack --config ./webpack/config.prod.babel.js --progress", "flow": "flow check src/js", "lint": "npx eslint ./src ./webpack", diff --git a/src/js/actions/TrezorConnectActions.js b/src/js/actions/TrezorConnectActions.js index eb7c64b6..9ad63574 100644 --- a/src/js/actions/TrezorConnectActions.js +++ b/src/js/actions/TrezorConnectActions.js @@ -117,7 +117,12 @@ export const init = (): AsyncAction => async (dispatch: Dispatch, getState: GetS debug: false, popup: false, webusb: true, - pendingTransportEvent: (getState().devices.length < 1) + pendingTransportEvent: (getState().devices.length < 1), + + // Use this if running 'yarn dev:local' + connectSrc: window.location.origin + '/', + // iframeSrc: window.location.origin + '/iframe.html', + // webusbSrc: window.location.origin + '/webusb.html', }); } catch (error) { // dispatch({ diff --git a/webpack/config.dev.local.babel.js b/webpack/config.dev.local.babel.js new file mode 100644 index 00000000..b4160fc7 --- /dev/null +++ b/webpack/config.dev.local.babel.js @@ -0,0 +1,164 @@ +import { + TREZOR_CONNECT_ROOT, + TREZOR_CONNECT_HTML, + TREZOR_CONNECT_FILES, + TREZOR_CONNECT, TREZOR_IFRAME, TREZOR_POPUP, TREZOR_WEBUSB, + SRC, + BUILD, + PORT +} from './constants'; + + +import webpack from 'webpack'; +import HtmlWebpackPlugin from 'html-webpack-plugin'; +import CopyWebpackPlugin from 'copy-webpack-plugin'; +import MiniCssExtractPlugin from 'mini-css-extract-plugin'; + +module.exports = { + watch: true, + mode: 'development', + devtool: 'inline-source-map', + entry: { + 'index': ['react-hot-loader/patch', `${SRC}js/index.js`], + 'trezor-connect-npm': `${TREZOR_CONNECT}.js`, + // 'extension-permissions': `${TREZOR_CONNECT_ROOT}src/js/extensionPermissions.js`, + 'iframe': TREZOR_IFRAME, + 'popup': TREZOR_POPUP, + 'webusb': TREZOR_WEBUSB, + }, + output: { + filename: '[name].[hash].js', + path: BUILD, + globalObject: 'this', // fix for HMR inside WebWorker from 'hd-wallet' + }, + devServer: { + contentBase: SRC, + hot: true, + https: false, + port: PORT, + stats: 'minimal', + inline: true, + }, + module: { + rules: [ + { + test: /\.jsx?$/, + exclude: /node_modules/, + use: ['babel-loader'] + }, + { + test: /\.less$/, + use: [ + { + loader: MiniCssExtractPlugin.loader, + options: { publicPath: '../' } + }, + 'css-loader', + 'less-loader', + ] + }, + { + test: /\.(png|gif|jpg)$/, + loader: 'file-loader?name=./images/[name].[ext]', + query: { + outputPath: './images', + name: '[name].[ext]', + } + }, + { + test: /\.(ttf|eot|svg|woff|woff2)$/, + loader: 'file-loader', + query: { + outputPath: './fonts', + name: '[name].[ext]', + }, + }, + { + type: 'javascript/auto', + test: /\.json/, + exclude: /(node_modules)/, + loader: 'file-loader', + query: { + outputPath: './data', + name: '[name].[ext]', + }, + }, + { + type: 'javascript/auto', + test: /\.wasm$/, + loader: 'file-loader', + query: { + name: 'js/[name].[ext]', + }, + }, + ], + }, + resolve: { + modules: [SRC, 'node_modules', `${TREZOR_CONNECT_ROOT}/node_modules`], + alias: { + 'trezor-connect': `${TREZOR_CONNECT}` + } + }, + performance: { + hints: false + }, + plugins: [ + new MiniCssExtractPlugin({ + filename: '[name].css', + chunkFilename: '[id].css', + }), + + new HtmlWebpackPlugin({ + chunks: ['index'], + template: `${SRC}index.html`, + filename: 'index.html', + inject: true + }), + + new HtmlWebpackPlugin({ + chunks: ['iframe'], + filename: `iframe.html`, + template: `${TREZOR_CONNECT_HTML}iframe.html`, + inject: false + }), + new HtmlWebpackPlugin({ + chunks: ['popup'], + filename: 'popup.html', + template: `${TREZOR_CONNECT_HTML}popup.html`, + inject: false + }), + new HtmlWebpackPlugin({ + chunks: ['webusb'], + filename: `webusb.html`, + template: `${TREZOR_CONNECT_HTML}webusb.html`, + inject: true + }), + // new HtmlWebpackPlugin({ + // chunks: ['extension-permissions'], + // filename: `extension-permissions.html`, + // template: `${TREZOR_CONNECT_HTML}extension-permissions.html`, + // inject: true + // }), + + new CopyWebpackPlugin([ + { from: TREZOR_CONNECT_FILES, to: 'data' }, + ]), + + new webpack.optimize.OccurrenceOrderPlugin(), + new webpack.NoEmitOnErrorsPlugin(), + new webpack.HotModuleReplacementPlugin(), + new webpack.NamedModulesPlugin(), + + new webpack.DefinePlugin({ + LOCAL: JSON.stringify(`http://localhost:${PORT}/`), + }), + + // ignore node lib from trezor-link + new webpack.IgnorePlugin(/\/iconv-loader$/), + ], + // ignoring "fs" import in fastxpub + node: { + fs: "empty", + path: "empty", + }, +} diff --git a/webpack/constants.js b/webpack/constants.js index 8717349e..92858a2f 100644 --- a/webpack/constants.js +++ b/webpack/constants.js @@ -9,9 +9,17 @@ const constants: Object = Object.freeze({ SRC: path.join(ABSOLUTE_BASE, 'src/'), PORT: 8081, INDEX: path.join(ABSOLUTE_BASE, 'src/index.html'), - TREZOR_CONNECT_ROOT: path.join(ABSOLUTE_BASE, '../trezor.js2/'), + TREZOR_CONNECT_ROOT: path.join(ABSOLUTE_BASE, '../trezor-connect/') }); +export const TREZOR_CONNECT_ROOT: string = constants.TREZOR_CONNECT_ROOT; +export const TREZOR_CONNECT: string = path.join(constants.TREZOR_CONNECT_ROOT, 'src/js/index'); +export const TREZOR_IFRAME: string = path.join(constants.TREZOR_CONNECT_ROOT, 'src/js/iframe/iframe.js'); +export const TREZOR_POPUP: string = path.join(constants.TREZOR_CONNECT_ROOT, 'src/js/popup/popup.js'); +export const TREZOR_WEBUSB: string = path.join(constants.TREZOR_CONNECT_ROOT, 'src/js/webusb/index.js'); +export const TREZOR_CONNECT_HTML: string = path.join(constants.TREZOR_CONNECT_ROOT, 'src/html/'); +export const TREZOR_CONNECT_FILES: string = path.join(constants.TREZOR_CONNECT_ROOT, 'src/data/'); + export const BUILD: string = constants.BUILD; export const SRC: string = constants.SRC; export const PORT: string = constants.PORT; From 4281259560126f97b375a5ca6a57ecdd47b4fa90 Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Tue, 7 Aug 2018 10:43:40 +0200 Subject: [PATCH 11/12] Resolve conflict after rebase --- src/js/actions/TrezorConnectActions.js | 75 ++++++++++---------------- 1 file changed, 29 insertions(+), 46 deletions(-) diff --git a/src/js/actions/TrezorConnectActions.js b/src/js/actions/TrezorConnectActions.js index 9ad63574..cc87cbbc 100644 --- a/src/js/actions/TrezorConnectActions.js +++ b/src/js/actions/TrezorConnectActions.js @@ -111,25 +111,25 @@ export const init = (): AsyncAction => async (dispatch: Dispatch, getState: GetS }); }); - try { - await TrezorConnect.init({ - transportReconnect: true, - debug: false, - popup: false, - webusb: true, - pendingTransportEvent: (getState().devices.length < 1), + try { + await TrezorConnect.init({ + connectSrc: 'http://localhost:8081/', + transportReconnect: true, + debug: false, + popup: false, + webusb: true, + pendingTransportEvent: (getState().devices.length < 1), - // Use this if running 'yarn dev:local' - connectSrc: window.location.origin + '/', - // iframeSrc: window.location.origin + '/iframe.html', - // webusbSrc: window.location.origin + '/webusb.html', - }); - } catch (error) { - // dispatch({ - // type: CONNECT.INITIALIZATION_ERROR, - // error - // }) - } + // Use this if running 'yarn dev:local' + connectSrc: window.location.origin + '/', + // iframeSrc: window.location.origin + '/iframe.html', + // webusbSrc: window.location.origin + '/webusb.html', + }); + } catch (error) { + // dispatch({ + // type: CONNECT.INITIALIZATION_ERROR, + // error + // }) } }; @@ -159,36 +159,20 @@ export const postInit = (): ThunkAction => (dispatch: Dispatch, getState: GetSta } if (devices.length > 0) { - const unacquired: ?TrezorDevice = devices.find(d => d.unacquired); + const unacquired: ?TrezorDevice = devices.find(d => d.type === 'unacquired'); if (unacquired) { - dispatch(onSelectDevice(unacquired)); + dispatch( onSelectDevice(unacquired) ); } else { const latest: Array = sortDevices(devices); const firstConnected: ?TrezorDevice = latest.find(d => d.connected); - dispatch(onSelectDevice(firstConnected || latest[0])); + dispatch( onSelectDevice(firstConnected || latest[0]) ); // TODO if (initialParams) { - if (!initialParams.hasOwnProperty('network') && initialPathname !== getState().router.location.pathname) { + if (!initialParams.hasOwnProperty("network") && initialPathname !== getState().router.location.pathname) { // dispatch( push(initialPathname) ); } else { - if (devices.length > 0) { - const unacquired: ?TrezorDevice = devices.find(d => d.type === 'unacquired'); - if (unacquired) { - dispatch( onSelectDevice(unacquired) ); - } else { - const latest: Array = 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) ); - } else { - - } } } } @@ -335,14 +319,13 @@ export const deviceDisconnect = (device: Device): AsyncAction => async (dispatch dispatch(DiscoveryActions.stop(selected)); } - const instances = getState().devices.filter(d => d.features && d.state && !d.remember && device.features && d.features.device_id === device.features.device_id); - if (instances.length > 0) { - dispatch({ - type: CONNECT.REMEMBER_REQUEST, - device: instances[0], - instances, - }); - } + const instances = getState().devices.filter(d => d.features && d.state && !d.remember && device.features && d.features.device_id === device.features.device_id); + if (instances.length > 0) { + dispatch({ + type: CONNECT.REMEMBER_REQUEST, + device: instances[0], + instances, + }); } } }; From 368c61d3c6e11d29d4320b3ea69f288dee571597 Mon Sep 17 00:00:00 2001 From: Vasek Mlejnsky Date: Tue, 7 Aug 2018 10:43:51 +0200 Subject: [PATCH 12/12] Update to latest Trezor Connect --- package.json | 2 +- yarn.lock | 11 ++++++++--- 2 files changed, 9 insertions(+), 4 deletions(-) diff --git a/package.json b/package.json index 125774f9..34cf05ab 100644 --- a/package.json +++ b/package.json @@ -54,7 +54,7 @@ "redux-raven-middleware": "^1.2.0", "redux-thunk": "^2.2.0", "styled-components": "^3.3.3", - "trezor-connect": "5.0.13", + "trezor-connect": "5.0.28", "web3": "^0.19.0", "webpack": "^4.16.3", "whatwg-fetch": "^2.0.4", diff --git a/yarn.lock b/yarn.lock index b411cf5d..6d8066e3 100644 --- a/yarn.lock +++ b/yarn.lock @@ -8787,9 +8787,14 @@ tr46@^1.0.1: dependencies: punycode "^2.1.0" -trezor-connect@5.0.13: - version "5.0.13" - resolved "https://registry.yarnpkg.com/trezor-connect/-/trezor-connect-5.0.13.tgz#2feee3d6644f8c3effd445b60ed80e7d5731469a" +trezor-connect@5.0.28: + version "5.0.28" + resolved "https://registry.yarnpkg.com/trezor-connect/-/trezor-connect-5.0.28.tgz#eb39bb0aa2a7555623251f0fb301233886fcdd09" + dependencies: + babel-polyfill "^6.26.0" + babel-runtime "^6.26.0" + events "^1.1.1" + whatwg-fetch "^2.0.4" trim-newlines@^1.0.0: version "1.0.0"