meriadec
7 years ago
32 changed files with 329 additions and 323 deletions
@ -1 +1,69 @@ |
|||||
export sync from './sync' |
// @flow
|
||||
|
|
||||
|
import CommNodeHid from '@ledgerhq/hw-transport-node-hid' |
||||
|
|
||||
|
import type { IPCSend } from 'types/electron' |
||||
|
|
||||
|
import scanAccountsOnDevice from './scanAccountsOnDevice' |
||||
|
import { verifyAddress, getFreshReceiveAddress } from './helpers' |
||||
|
|
||||
|
import sync from './sync' |
||||
|
|
||||
|
export default { |
||||
|
sync, |
||||
|
scan: async ( |
||||
|
send: IPCSend, |
||||
|
{ |
||||
|
devicePath, |
||||
|
currencyId, |
||||
|
}: { |
||||
|
devicePath: string, |
||||
|
currencyId: string, |
||||
|
}, |
||||
|
) => { |
||||
|
try { |
||||
|
send('accounts.scanAccountsOnDevice.start', { pid: process.pid }, { kill: false }) |
||||
|
const accounts = await scanAccountsOnDevice({ |
||||
|
devicePath, |
||||
|
currencyId, |
||||
|
onAccountScanned: account => { |
||||
|
send('accounts.scanAccountsOnDevice.accountScanned', account, { kill: false }) |
||||
|
}, |
||||
|
}) |
||||
|
send('accounts.scanAccountsOnDevice.success', accounts) |
||||
|
} catch (err) { |
||||
|
send('accounts.scanAccountsOnDevice.fail', err) |
||||
|
} |
||||
|
}, |
||||
|
|
||||
|
getFreshReceiveAddress: async ( |
||||
|
send: IPCSend, |
||||
|
{ |
||||
|
currencyId, |
||||
|
accountIndex, |
||||
|
}: { |
||||
|
currencyId: string, |
||||
|
accountIndex: number, |
||||
|
}, |
||||
|
) => { |
||||
|
try { |
||||
|
const freshAddress = await getFreshReceiveAddress({ currencyId, accountIndex }) |
||||
|
send('accounts.getFreshReceiveAddress.success', freshAddress) |
||||
|
} catch (err) { |
||||
|
send('accounts.getFreshReceiveAddress.fail', err) |
||||
|
} |
||||
|
}, |
||||
|
|
||||
|
verifyAddress: async ( |
||||
|
send: IPCSend, |
||||
|
{ pathDevice, path }: { pathDevice: string, path: string }, |
||||
|
) => { |
||||
|
const transport = await CommNodeHid.open(pathDevice) |
||||
|
try { |
||||
|
await verifyAddress({ transport, path }) |
||||
|
send('accounts.verifyAddress.success') |
||||
|
} catch (err) { |
||||
|
send('accounts.verifyAddress.fail') |
||||
|
} |
||||
|
}, |
||||
|
} |
||||
|
@ -1,7 +1,7 @@ |
|||||
// @flow
|
// @flow
|
||||
|
|
||||
export default (send: Function) => ({ |
import type { IPCSend } from 'types/electron' |
||||
all: () => { |
|
||||
setTimeout(() => send('accounts.sync.success'), 5e3) |
export default (send: IPCSend) => { |
||||
}, |
setTimeout(() => send('accounts.sync.success'), 5e3) |
||||
}) |
} |
||||
|
@ -0,0 +1,44 @@ |
|||||
|
// @flow
|
||||
|
|
||||
|
import CommNodeHid from '@ledgerhq/hw-transport-node-hid' |
||||
|
import Btc from '@ledgerhq/hw-app-btc' |
||||
|
|
||||
|
import type { IPCSend } from 'types/electron' |
||||
|
|
||||
|
import { getPath } from 'internals/accounts/helpers' |
||||
|
|
||||
|
export default async ( |
||||
|
send: IPCSend, |
||||
|
{ |
||||
|
currencyId, |
||||
|
devicePath, |
||||
|
accountPath, |
||||
|
accountAddress, |
||||
|
segwit = true, |
||||
|
}: { |
||||
|
currencyId?: string, |
||||
|
devicePath: string, |
||||
|
accountPath: string, |
||||
|
accountAddress: string, |
||||
|
segwit: boolean, |
||||
|
}, |
||||
|
) => { |
||||
|
try { |
||||
|
const transport = await CommNodeHid.open(devicePath) |
||||
|
const btc = new Btc(transport) |
||||
|
if (accountPath) { |
||||
|
const { bitcoinAddress } = await btc.getWalletPublicKey(accountPath, false, segwit) |
||||
|
if (bitcoinAddress === accountAddress) { |
||||
|
send('devices.checkIfAppOpened.success', { devicePath }) |
||||
|
} else { |
||||
|
throw new Error('Address is different') |
||||
|
} |
||||
|
} |
||||
|
if (currencyId) { |
||||
|
await btc.getWalletPublicKey(getPath({ currencyId, segwit }), false, segwit) |
||||
|
send('devices.checkIfAppOpened.success', { devicePath }) |
||||
|
} |
||||
|
} catch (err) { |
||||
|
send('devices.checkIfAppOpened.fail', { devicePath }) |
||||
|
} |
||||
|
} |
@ -0,0 +1,2 @@ |
|||||
|
export listen from './listen' |
||||
|
export checkIfAppOpened from './checkIfAppOpened' |
@ -0,0 +1,24 @@ |
|||||
|
// @flow
|
||||
|
|
||||
|
import CommNodeHid from '@ledgerhq/hw-transport-node-hid' |
||||
|
import noop from 'lodash/noop' |
||||
|
|
||||
|
import type { IPCSend } from 'types/electron' |
||||
|
|
||||
|
export default (send: IPCSend) => { |
||||
|
CommNodeHid.listen({ |
||||
|
error: noop, |
||||
|
complete: noop, |
||||
|
next: async e => { |
||||
|
if (!e.device) { |
||||
|
return |
||||
|
} |
||||
|
if (e.type === 'add') { |
||||
|
send('device.add', e.device, { kill: false }) |
||||
|
} |
||||
|
if (e.type === 'remove') { |
||||
|
send('device.remove', e.device, { kill: false }) |
||||
|
} |
||||
|
}, |
||||
|
}) |
||||
|
} |
@ -0,0 +1,12 @@ |
|||||
|
// @flow
|
||||
|
|
||||
|
import type { IPCSend } from 'types/electron' |
||||
|
|
||||
|
import { createTransportHandler, getMemInfos } from './helpers' |
||||
|
|
||||
|
export default (send: IPCSend, data: any) => |
||||
|
createTransportHandler(send, { |
||||
|
action: getMemInfos, |
||||
|
successResponse: 'manager.getMemInfosSuccess', |
||||
|
errorResponse: 'manager.getMemInfosError', |
||||
|
})(data) |
@ -0,0 +1,22 @@ |
|||||
|
// @flow
|
||||
|
|
||||
|
/** |
||||
|
* Manager |
||||
|
* ------- |
||||
|
* |
||||
|
* xXx |
||||
|
* xXx |
||||
|
* xXx |
||||
|
* xxxXxxx |
||||
|
* xxXxx |
||||
|
* xXx |
||||
|
* xX x Xx |
||||
|
* xX Xx |
||||
|
* xxXXXXXXXxx |
||||
|
* |
||||
|
*/ |
||||
|
|
||||
|
export { default as getMemInfos } from './getMemInfos' |
||||
|
export { default as installApp } from './installApp' |
||||
|
export { default as listApps } from './listApps' |
||||
|
export { default as uninstallApp } from './uninstallApp' |
@ -0,0 +1,12 @@ |
|||||
|
// @flow
|
||||
|
|
||||
|
import type { IPCSend } from 'types/electron' |
||||
|
|
||||
|
import { createTransportHandler, installApp } from './helpers' |
||||
|
|
||||
|
export default (send: IPCSend, data: any) => |
||||
|
createTransportHandler(send, { |
||||
|
action: installApp, |
||||
|
successResponse: 'manager.appInstalled', |
||||
|
errorResponse: 'manager.appInstallError', |
||||
|
})(data) |
@ -0,0 +1,14 @@ |
|||||
|
// @flow
|
||||
|
|
||||
|
import axios from 'axios' |
||||
|
|
||||
|
import type { IPCSend } from 'types/electron' |
||||
|
|
||||
|
export default async (send: IPCSend) => { |
||||
|
try { |
||||
|
const { data } = await axios.get('https://api.ledgerwallet.com/update/applications') |
||||
|
send('manager.listAppsSuccess', data['nanos-1.4']) |
||||
|
} catch (err) { |
||||
|
send('manager.listAppsError', { message: err.message, stack: err.stack }) |
||||
|
} |
||||
|
} |
@ -0,0 +1,12 @@ |
|||||
|
// @flow
|
||||
|
|
||||
|
import type { IPCSend } from 'types/electron' |
||||
|
|
||||
|
import { createTransportHandler, uninstallApp } from './helpers' |
||||
|
|
||||
|
export default (send: IPCSend, data: any) => |
||||
|
createTransportHandler(send, { |
||||
|
action: uninstallApp, |
||||
|
successResponse: 'manager.appUninstalled', |
||||
|
errorResponse: 'manager.appUninstallError', |
||||
|
})(data) |
@ -1,28 +0,0 @@ |
|||||
// @flow
|
|
||||
|
|
||||
import CommNodeHid from '@ledgerhq/hw-transport-node-hid' |
|
||||
import noop from 'lodash/noop' |
|
||||
|
|
||||
import type { IPCSend } from 'types/electron' |
|
||||
|
|
||||
export default (send: IPCSend) => ({ |
|
||||
listen: () => { |
|
||||
CommNodeHid.listen({ |
|
||||
error: noop, |
|
||||
complete: noop, |
|
||||
next: async e => { |
|
||||
if (!e.device) { |
|
||||
return |
|
||||
} |
|
||||
|
|
||||
if (e.type === 'add') { |
|
||||
send('device.add', e.device, { kill: false }) |
|
||||
} |
|
||||
|
|
||||
if (e.type === 'remove') { |
|
||||
send('device.remove', e.device, { kill: false }) |
|
||||
} |
|
||||
}, |
|
||||
}) |
|
||||
}, |
|
||||
}) |
|
@ -1,3 +0,0 @@ |
|||||
export devices from './devices' |
|
||||
export wallet from './wallet' |
|
||||
export manager from './manager' |
|
@ -1,50 +0,0 @@ |
|||||
// @flow
|
|
||||
|
|
||||
/** |
|
||||
* Manager |
|
||||
* ------- |
|
||||
* |
|
||||
* xXx |
|
||||
* xXx |
|
||||
* xXx |
|
||||
* xxxXxxx |
|
||||
* xxXxx |
|
||||
* xXx |
|
||||
* xX x Xx |
|
||||
* xX Xx |
|
||||
* xxXXXXXXXxx |
|
||||
* |
|
||||
*/ |
|
||||
|
|
||||
import type { IPCSend } from 'types/electron' |
|
||||
import axios from 'axios' |
|
||||
import { createTransportHandler, installApp, uninstallApp, getMemInfos } from './helpers' |
|
||||
|
|
||||
export default (send: IPCSend) => ({ |
|
||||
installApp: createTransportHandler(send, { |
|
||||
action: installApp, |
|
||||
successResponse: 'device.appInstalled', |
|
||||
errorResponse: 'device.appInstallError', |
|
||||
}), |
|
||||
|
|
||||
uninstallApp: createTransportHandler(send, { |
|
||||
action: uninstallApp, |
|
||||
successResponse: 'device.appUninstalled', |
|
||||
errorResponse: 'device.appUninstallError', |
|
||||
}), |
|
||||
|
|
||||
getMemInfos: createTransportHandler(send, { |
|
||||
action: getMemInfos, |
|
||||
successResponse: 'device.getMemInfosSuccess', |
|
||||
errorResponse: 'device.getMemInfosError', |
|
||||
}), |
|
||||
|
|
||||
listApps: async () => { |
|
||||
try { |
|
||||
const { data } = await axios.get('https://api.ledgerwallet.com/update/applications') |
|
||||
send('manager.listAppsSuccess', data['nanos-1.4']) |
|
||||
} catch (err) { |
|
||||
send('manager.listAppsError', { message: err.message, stack: err.stack }) |
|
||||
} |
|
||||
}, |
|
||||
}) |
|
@ -1,105 +0,0 @@ |
|||||
// @flow
|
|
||||
|
|
||||
import CommNodeHid from '@ledgerhq/hw-transport-node-hid' |
|
||||
import Btc from '@ledgerhq/hw-app-btc' |
|
||||
|
|
||||
import { getPath, verifyAddress, getFreshReceiveAddress } from './accounts' |
|
||||
import scanAccountsOnDevice from './scanAccountsOnDevice' |
|
||||
|
|
||||
export default (sendEvent: Function) => ({ |
|
||||
/** |
|
||||
* Scan all the accounts for the given device and currency and returns them |
|
||||
*/ |
|
||||
scanAccountsOnDevice: async ({ |
|
||||
devicePath, |
|
||||
currencyId, |
|
||||
}: { |
|
||||
devicePath: string, |
|
||||
currencyId: string, |
|
||||
}) => { |
|
||||
try { |
|
||||
sendEvent('wallet.scanAccountsOnDevice.start', { pid: process.pid }, { kill: false }) |
|
||||
const accounts = await scanAccountsOnDevice({ |
|
||||
devicePath, |
|
||||
currencyId, |
|
||||
onAccountScanned: account => { |
|
||||
sendEvent('wallet.scanAccountsOnDevice.accountScanned', account, { kill: false }) |
|
||||
}, |
|
||||
}) |
|
||||
sendEvent('wallet.scanAccountsOnDevice.success', accounts) |
|
||||
} catch (err) { |
|
||||
sendEvent('wallet.scanAccountsOnDevice.fail', err) |
|
||||
} |
|
||||
}, |
|
||||
getAccounts: async ({ |
|
||||
pathDevice, |
|
||||
currencyId, |
|
||||
currentAccounts, |
|
||||
}: { |
|
||||
pathDevice: string, |
|
||||
currencyId: string, |
|
||||
currentAccounts: Array<string>, |
|
||||
}) => { |
|
||||
console.warn( |
|
||||
`NOT IMPLEMENTED: getting account for ${pathDevice} ${currencyId} ${currentAccounts.length}`, |
|
||||
) |
|
||||
}, |
|
||||
getFreshReceiveAddress: async ({ |
|
||||
currencyId, |
|
||||
accountIndex, |
|
||||
}: { |
|
||||
currencyId: string, |
|
||||
accountIndex: number, |
|
||||
}) => { |
|
||||
try { |
|
||||
console.log(accountIndex) |
|
||||
const freshAddress = await getFreshReceiveAddress({ currencyId, accountIndex }) |
|
||||
sendEvent('wallet.getFreshReceiveAddress.success', freshAddress) |
|
||||
} catch (err) { |
|
||||
sendEvent('wallet.getFreshReceiveAddress.fail', err) |
|
||||
} |
|
||||
}, |
|
||||
verifyAddress: async ({ pathDevice, path }: { pathDevice: string, path: string }) => { |
|
||||
const transport = await CommNodeHid.open(pathDevice) |
|
||||
|
|
||||
try { |
|
||||
await verifyAddress({ transport, path }) |
|
||||
|
|
||||
sendEvent('wallet.verifyAddress.success') |
|
||||
} catch (err) { |
|
||||
sendEvent('wallet.verifyAddress.fail') |
|
||||
} |
|
||||
}, |
|
||||
checkIfAppOpened: async ({ |
|
||||
currencyId, |
|
||||
devicePath, |
|
||||
accountPath, |
|
||||
accountAddress, |
|
||||
segwit = true, |
|
||||
}: { |
|
||||
currencyId?: string, |
|
||||
devicePath: string, |
|
||||
accountPath: string, |
|
||||
accountAddress: string, |
|
||||
segwit: boolean, |
|
||||
}) => { |
|
||||
try { |
|
||||
const transport = await CommNodeHid.open(devicePath) |
|
||||
const btc = new Btc(transport) |
|
||||
if (accountPath) { |
|
||||
const { bitcoinAddress } = await btc.getWalletPublicKey(accountPath, false, segwit) |
|
||||
if (bitcoinAddress === accountAddress) { |
|
||||
sendEvent('wallet.checkIfAppOpened.success', { devicePath }) |
|
||||
} else { |
|
||||
throw new Error('Address is different') |
|
||||
} |
|
||||
} |
|
||||
if (currencyId) { |
|
||||
await btc.getWalletPublicKey(getPath({ currencyId, segwit }), false, segwit) |
|
||||
sendEvent('wallet.checkIfAppOpened.success', { devicePath }) |
|
||||
} |
|
||||
} catch (err) { |
|
||||
sendEvent('wallet.checkIfAppOpened.fail', { devicePath }) |
|
||||
} |
|
||||
}, |
|
||||
}) |
|
@ -0,0 +1,34 @@ |
|||||
|
// @flow
|
||||
|
|
||||
|
import { ipcRenderer } from 'electron' |
||||
|
|
||||
|
export default function runJob({ |
||||
|
channel, |
||||
|
job, |
||||
|
successResponse, |
||||
|
errorResponse, |
||||
|
data, |
||||
|
}: { |
||||
|
channel: string, |
||||
|
job: string, |
||||
|
successResponse: string, |
||||
|
errorResponse: string, |
||||
|
data?: any, |
||||
|
}): Promise<void> { |
||||
|
return new Promise((resolve, reject) => { |
||||
|
ipcRenderer.send(channel, { type: job, data }) |
||||
|
ipcRenderer.on('msg', handler) |
||||
|
function handler(e, res) { |
||||
|
const { type, data } = res |
||||
|
if (![successResponse, errorResponse].includes(type)) { |
||||
|
return |
||||
|
} |
||||
|
ipcRenderer.removeListener('msg', handler) |
||||
|
if (type === successResponse) { |
||||
|
resolve(data) |
||||
|
} else if (type === errorResponse) { |
||||
|
reject(data) |
||||
|
} |
||||
|
} |
||||
|
}) |
||||
|
} |
Loading…
Reference in new issue