import * as bip32 from 'bip32' import React from 'react' import Maybe from 'folktale/maybe' import { Button } from '../components/Base' import { Row, Col, H1, P, H2 } from '../components/Base' import { Input, InnerLabel } from '../components/Base' import Transport from '@ledgerhq/hw-transport-u2f' import Eth from '@ledgerhq/hw-app-eth' import * as secp256k1 from 'secp256k1' import { LEDGER_BASE_PATH } from '../lib/ledger' import { ROUTE_NAMES } from '../lib/router' const chopHdPrefix = str => str.slice(0, 2) === "m/" ? str.slice(2) : str const addHdPrefix = str => str.slice(0, 2) === "m/" ? str : "m/" + str class Ledger extends React.Component { constructor(props) { super(props) this.state = { hdpath: LEDGER_BASE_PATH } this.pollDevice = this.pollDevice.bind(this) this.handleHdPathInput = this.handleHdPathInput.bind(this) } handleHdPathInput(hdpath) { this.setState({ hdpath }) } async pollDevice() { const { setWallet, setWalletHdPath } = this.props const { hdpath } = this.state const transport = await Transport.create() const eth = new Eth(transport) const path = chopHdPrefix(hdpath) eth.getAddress(path, false, true) .then(info => { const publicKey = Buffer.from(info.publicKey, 'hex') const chainCode = Buffer.from(info.chainCode, 'hex') const pub = secp256k1.publicKeyConvert(publicKey, true) const hd = bip32.fromPublicKey(pub, chainCode) setWallet(Maybe.Just(hd)) setWalletHdPath(addHdPrefix(hdpath)) }, _ => { setWallet(Maybe.Nothing()) }) } render() { const { pushRoute, popRoute, wallet } = this.props const { hdpath } = this.state return (

{ 'Authenticate With Your Ledger' }

{'Running on HTTPS?'}

{ `Connect and authenticate to your Ledger, and then open the "Ethereum" application. If you're running on older firmware, make sure the "browser support" option is turned on. To sign transactions, you'll also need to enable the "contract data" option.` }

{ `If you'd like to use a custom derivation path, you may enter it below.` }

{'Running on HTTP?'}

{`To authenticate and sign transactions with a Ledger, Bridge must be serving over HTTPS on localhost. You can do this via the following:`}

  1. {'Install'} {'mkcert'}
  2. {'Install a local certificate authority via '}{'mkcert -install'}
  3. {'In your '}{'bridge'}{' directory, generate a certificate valid for localhost via '} {'mkcert localhost'}{'.'} {'This will produce two files: '}{'localhost.pem'} {', the local certificate, and '}{'localhost-key.pem'}{', its corresponding private key.'}
  4. {'Run '}{'python bridge-https.py'}
{'HD Path'}
) } } export default Ledger