1import { Just, Nothing } from 'folktale/maybe'
2import * as lodash from 'lodash'
3import * as azimuth from 'azimuth-js'
4import { Stack } from 'immutable'
5import { CONTRACT_ADDRESSES } from './lib/contracts'
6import React from 'react'
9import Footer from './components/Footer'
10import Header from './components/Header'
11import { Container, Row, Col } from './components/Base'
13import { ROUTE_NAMES, router } from './lib/router'
14import { NETWORK_NAMES } from './lib/network'
15import { WALLET_NAMES, DEFAULT_HD_PATH, walletFromMnemonic } from './lib/wallet'
16import { BRIDGE_ERROR } from './lib/error'
18const initWeb3 = (networkType) => {
19 if (networkType === NETWORK_NAMES.MAINNET) {
21 `https://mainnet.infura.io/v3/${process.env.REACT_APP_INFURA_ENDPOINT}`
23 const provider = new Web3.providers.HttpProvider(endpoint)
24 const web3 = new Web3(provider)
25 const contracts = azimuth.initContracts(web3, CONTRACT_ADDRESSES.MAINNET)
26 return {web3: web3, contracts: contracts}
27 } else if (networkType === NETWORK_NAMES.LOCAL) {
29 process.env.NODE_ENV === 'development'
32 const endpoint = `${protocol}://localhost:8545`
33 const provider = new Web3.providers.WebsocketProvider(endpoint)
34 const web3 = new Web3(provider)
35 const contracts = azimuth.initContracts(web3, CONTRACT_ADDRESSES.DEV)
36 return {web3: web3, contracts: contracts}
40class Bridge extends React.Component {
46 process.env.NODE_ENV === 'development'
48 : NETWORK_NAMES.MAINNET
50 // Sidestepping full network selection to allow for point viewing,
51 // but still respecting the networkType
52 const { web3, contracts } = initWeb3(networkType)
56 // Note that the 'wallet' prop has type depending on the 'walletType' prop.
57 // These could be bound together in a single structure (so that
58 // 'walletType' acted more explicitly as a data constructor of sorts) but
59 // it doesn't necessarily help us much, since we branch on 'walletType'
60 // before setting 'wallet'.
62 // Wallets are always wrapped in Maybe. For most authentication
63 // mechanisms, Maybe wraps a BIP32 HD wallet; for Ethereum private keys,
64 // JSON keystore files, and Metamask authentication, it wraps an
69 routeCrumbs: Stack([ ROUTE_NAMES.LANDING ]),
72 networkType: networkType,
74 contracts: Just(contracts),
76 walletType: WALLET_NAMES.MNEMONIC,
78 walletHdPath: DEFAULT_HD_PATH,
79 // urbit wallet-related
80 urbitWallet: Nothing(),
81 authMnemonic: Nothing(),
82 networkSeedCache: null,
84 pointCursor: Nothing(),
87 txnHashCursor: Nothing(),
91 this.pushRoute = this.pushRoute.bind(this)
92 this.popRoute = this.popRoute.bind(this)
93 this.skipRoute = this.skipRoute.bind(this)
94 this.setNetworkType = this.setNetworkType.bind(this)
95 this.setNetwork = this.setNetwork.bind(this)
96 this.setWalletType = this.setWalletType.bind(this)
97 this.setWallet = this.setWallet.bind(this)
98 this.setWalletHdPath = this.setWalletHdPath.bind(this)
99 this.setUrbitWallet = this.setUrbitWallet.bind(this)
100 this.setAuthMnemonic = this.setAuthMnemonic.bind(this)
101 this.setPointCursor = this.setPointCursor.bind(this)
102 this.setTxnHashCursor = this.setTxnHashCursor.bind(this)
103 this.setTxnConfirmations = this.setTxnConfirmations.bind(this)
104 this.setNetworkSeedCache = this.setNetworkSeedCache.bind(this)
105 this.addToPointCache = this.addToPointCache.bind(this)
108 componentDidMount() {
109 window.history.pushState(null, null, null);
111 window.onpopstate = (e) => {
112 window.history.pushState(null, null, null);
118 // If running in development, the following can be tweaked to get you set
119 // up with a desirable initial state.
121 // if (process.env.NODE_ENV === 'development') {
123 // const socket = 'ws://localhost:8545'
124 // const provider = new Web3.providers.WebsocketProvider(socket)
125 // const web3 = new Web3(provider)
126 // const contracts = azimuth.initContracts(web3, CONTRACT_ADDRESSES.DEV)
128 // const mnemonic = process.env.REACT_APP_DEV_MNEMONIC
129 // const hdpath = process.env.REACT_APP_HD_PATH
132 // routeCrumbs: Stack([
133 // // ROUTE_NAMES.CREATE_GALAXY,
134 // // ROUTE_NAMES.SHIP,
135 // ROUTE_NAMES.SHIPS,
136 // // ROUTE_NAMES.MNEMONIC,
137 // ROUTE_NAMES.WALLET,
138 // ROUTE_NAMES.NETWORK,
139 // ROUTE_NAMES.LANDING
141 // networkType: NETWORK_NAMES.LOCAL,
142 // pointCursor: Just(0),
144 // contracts: Just(contracts),
145 // walletType: WALLET_NAMES.MNEMONIC,
146 // wallet: walletFromMnemonic(mnemonic, hdpath),
147 // urbitWallet: Nothing(),
148 // authMnemonic: Just('benefit crew supreme gesture quantum web media hazard theory mercy wing kitten')
153 pushRoute(symbol, routeData) {
154 if (lodash.includes(ROUTE_NAMES, symbol)) {
155 this.setState((state, _) => ({
156 routeCrumbs: state.routeCrumbs.push(symbol),
160 // Scroll to top of page with each route transition.
161 window.scrollTo(0, 0);
164 throw BRIDGE_ERROR.INVALID_ROUTE
169 this.setState((state, _) => ({
170 routeCrumbs: state.routeCrumbs.skip(len)
175 this.setState((state, _) => ({
176 routeCrumbs: state.routeCrumbs.shift()
180 setNetworkType(symbol) {
181 if (lodash.includes(NETWORK_NAMES, symbol)) {
186 throw BRIDGE_ERROR.INVALID_NETWORK_TYPE
190 setNetworkSeedCache(networkSeed, revision) {
192 networkSeedCache: networkSeed,
193 networkRevisionCache: revision
197 setNetwork(web3, contracts) {
204 setWalletType(symbol) {
205 if (lodash.includes(WALLET_NAMES, symbol)) {
210 throw BRIDGE_ERROR.INVALID_WALLET_TYPE
215 this.setState({ wallet })
218 setWalletHdPath(walletHdPath) {
219 this.setState({ walletHdPath })
222 // also sets wallet to ownership address
223 setUrbitWallet(urbitWallet) {
224 let wallet = this.state.wallet;
225 if (Just.hasInstance(urbitWallet)) {
226 const mnemonic = urbitWallet.value.ownership.seed;
227 wallet = walletFromMnemonic(
230 urbitWallet.value.meta.passphrase
233 this.setState({ urbitWallet, wallet })
236 setAuthMnemonic(authMnemonic) {
237 this.setState({ authMnemonic })
240 setPointCursor(pointCursor) {
241 this.setState({ pointCursor })
244 addToPointCache(entry) {
245 this.setState((state, _) => ({
246 pointCache: Object.assign(state.pointCache, entry)
250 setTxnHashCursor(txnHashCursor) {
251 this.setState({ txnHashCursor })
254 setTxnConfirmations(txnHash, txnConfirmations) {
255 this.setState((prevState, _) => {
256 return prevState.routeCrumbs.peek() === ROUTE_NAMES.SENT_TRANSACTION
257 ? {txnConfirmations: { ...prevState.txnConfirmations,
258 [txnHash]: txnConfirmations}}
274 networkRevisionCache,
283 const View = router(routeCrumbs.peek())
285 // For the invite acceptance flow, widen the screen to use the full
286 // container, and hide the breadcrumbs
287 const colClass = routeCrumbs.contains(ROUTE_NAMES.INVITE_TICKET)
289 : 'col-md-offset-1 col-md-10'
291 const colStyle = routeCrumbs.contains(ROUTE_NAMES.INVITE_TICKET)
293 : {maxWidth: '620px'}
295 const showCrumbs = routeCrumbs.contains(ROUTE_NAMES.INVITE_TICKET)
302 <Col className={colClass} style={colStyle}>
304 routeCrumbs={ routeCrumbs }
305 skipRoute={ this.skipRoute }
306 networkType={ networkType }
308 showCrumbs={ showCrumbs }
309 pointCursor={ pointCursor } />
311 <Row className={ 'row wrapper' }>
315 pushRoute={ this.pushRoute }
316 popRoute={ this.popRoute }
317 routeData={ routeData }
319 setNetworkType={ this.setNetworkType }
320 setNetwork={ this.setNetwork }
321 networkType={ networkType }
323 contracts={ contracts }
325 setWalletType={ this.setWalletType }
326 setWalletHdPath={ this.setWalletHdPath }
327 setWallet={ this.setWallet }
328 walletType={ walletType }
329 walletHdPath={ walletHdPath }
332 urbitWallet={ urbitWallet }
333 setUrbitWallet={ this.setUrbitWallet }
334 authMnemonic={ authMnemonic }
335 setAuthMnemonic={ this.setAuthMnemonic }
337 setPointCursor={ this.setPointCursor }
338 addToPointCache={ this.addToPointCache }
339 pointCursor={ pointCursor }
340 pointCache={ pointCache }
341 networkSeedCache= { networkSeedCache }
342 networkRevisionCache={ networkRevisionCache }
343 setNetworkSeedCache= { this.setNetworkSeedCache }
345 setTxnHashCursor={ this.setTxnHashCursor }
346 txnHashCursor={ txnHashCursor }
347 setTxnConfirmations={ this.setTxnConfirmations }
348 txnConfirmations={ txnConfirmations } />
350 <div className={'push'} />
keysesc to close
- j k
- move down, up
- enter
- open
- esc
- back, or up a level
- 1 2 3 4
- readme, files, commits, refs
- /
- filter
- y
- copy the clone command
- c
- compare the chosen commit with another (or shift-click both)
- ?
- show or hide this list