From e47661b94e6665347946354e7995fddf2a4770c6 Mon Sep 17 00:00:00 2001 From: Ezerous Date: Mon, 7 Sep 2020 13:58:02 +0300 Subject: [PATCH] Add support for reload on network/account change, refactoring --- package.json | 2 +- src/Drizzle.js | 9 ++---- src/DrizzleContract.js | 4 +-- src/accounts/accountsActions.js | 5 ++-- src/accounts/accountsMiddleware.js | 9 ++++-- src/accounts/accountsReducer.js | 4 +-- src/accounts/accountsSaga.js | 6 ++-- src/contracts/constants.js | 8 +++--- src/contracts/contractsReducer.js | 2 +- src/contracts/contractsSaga.js | 8 +++--- src/defaultOptions.js | 2 ++ .../drizzleActions.js | 0 .../drizzleMiddleware.js} | 28 +++++++++++++++---- .../drizzleStatusReducer.js | 0 .../drizzleStatusSaga.js | 8 +++--- src/generateStore.js | 10 +++---- src/index.js | 18 +++--------- src/reducer.js | 20 ------------- src/root/rootMiddleware.js | 11 ++++++++ src/root/rootReducer.js | 20 +++++++++++++ src/root/rootSaga.js | 13 +++++++++ src/rootSaga.js | 11 -------- src/web3/web3Actions.js | 21 +++++++++----- src/web3/web3Middleware.js | 18 ++++++------ src/web3/web3Reducer.js | 11 ++++---- src/web3/web3Saga.js | 25 ++++++++++++----- 26 files changed, 158 insertions(+), 115 deletions(-) rename src/{drizzleStatus => drizzle}/drizzleActions.js (100%) rename src/{drizzle-middleware.js => drizzle/drizzleMiddleware.js} (59%) rename src/{drizzleStatus => drizzle}/drizzleStatusReducer.js (100%) rename src/{drizzleStatus => drizzle}/drizzleStatusSaga.js (90%) delete mode 100644 src/reducer.js create mode 100644 src/root/rootMiddleware.js create mode 100644 src/root/rootReducer.js create mode 100644 src/root/rootSaga.js delete mode 100644 src/rootSaga.js diff --git a/package.json b/package.json index f0d2909..d21bc50 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@ezerous/drizzle", - "version": "0.2.1", + "version": "0.3.0", "description": "A reactive data-store for web3 and smart contracts.", "license": "MIT", "author": "Ezerous ", diff --git a/src/Drizzle.js b/src/Drizzle.js index ee40798..59bd819 100644 --- a/src/Drizzle.js +++ b/src/Drizzle.js @@ -3,7 +3,7 @@ import defaultOptions from './defaultOptions' import merge from './mergeOptions' import DrizzleContract from './DrizzleContract' import * as ContractActions from './contracts/constants' -import * as DrizzleActions from './drizzleStatus/drizzleActions' +import * as DrizzleActions from './drizzle/drizzleActions' // Load as promise so that async Drizzle initialization can still resolve const isEnvReadyPromise = new Promise((resolve) => { @@ -81,11 +81,8 @@ class Drizzle { events ) - if (this.contracts[drizzleContract.contractName]) { - throw new Error( - `Contract already exists: ${drizzleContract.contractName}` - ) - } + if (this.contracts[drizzleContract.contractName]) + console.warn(`Adding an already existing contract: ${drizzleContract.contractName}.\nIgnore this if upon drizzle reinitialization.`); this.store.dispatch({ type: ContractActions.CONTRACT_INITIALIZING, contractConfig }) diff --git a/src/DrizzleContract.js b/src/DrizzleContract.js index 8d1a946..70f0d8e 100644 --- a/src/DrizzleContract.js +++ b/src/DrizzleContract.js @@ -38,14 +38,14 @@ class DrizzleContract { if (typeof event === 'object') { store.dispatch({ - type: ContractActions.LISTEN_FOR_EVENT, + type: ContractActions.CONTRACT_EVENT_LISTEN, contract: this, eventName: event.eventName, eventOptions: event.eventOptions }) } else { store.dispatch({ - type: ContractActions.LISTEN_FOR_EVENT, + type: ContractActions.CONTRACT_EVENT_LISTEN, contract: this, eventName: event }) diff --git a/src/accounts/accountsActions.js b/src/accounts/accountsActions.js index 6c69625..c090258 100644 --- a/src/accounts/accountsActions.js +++ b/src/accounts/accountsActions.js @@ -1,11 +1,12 @@ export const ACCOUNTS_FETCHING = 'ACCOUNTS_FETCHING' export const ACCOUNTS_FETCHED = 'ACCOUNTS_FETCHED' +export const ACCOUNTS_CHANGED = 'ACCOUNTS_CHANGED' export const ACCOUNTS_FAILED = 'ACCOUNTS_FAILED' export const ACCOUNTS_LISTENING = 'ACCOUNTS_LISTENING' -export function accountsFetched (accounts) { +export function accountsChanged (accounts) { return { - type: ACCOUNTS_FETCHED, + type: ACCOUNTS_CHANGED, accounts } } diff --git a/src/accounts/accountsMiddleware.js b/src/accounts/accountsMiddleware.js index 4c9128f..2e5b3fa 100644 --- a/src/accounts/accountsMiddleware.js +++ b/src/accounts/accountsMiddleware.js @@ -1,5 +1,5 @@ -import { WEB3_INITIALIZED } from '../web3/web3Actions' -import { accountsFetched, accountsListening } from './accountsActions' +import { networkIdChanged, WEB3_INITIALIZED } from '../web3/web3Actions' +import { accountsChanged, accountsFetched, accountsListening } from './accountsActions' export const accountsMiddleware = web3 => store => next => action => { const { type } = action @@ -13,7 +13,10 @@ export const accountsMiddleware = web3 => store => next => action => { // For some reason accounts here are returned with lowercase letters, so we need to patch them let patchedAccounts = Array.from(accounts); patchedAccounts.forEach((account, i) => patchedAccounts[i] = web3.utils.toChecksumAddress(account)); - store.dispatch(accountsFetched(patchedAccounts)); + + const storedAccounts = store.getState().accounts; + if(storedAccounts[0] && (patchedAccounts[0] !== storedAccounts[0])) + store.dispatch(accountsChanged(patchedAccounts)); }); store.dispatch(accountsListening()); } diff --git a/src/accounts/accountsReducer.js b/src/accounts/accountsReducer.js index 5b045e6..d292885 100644 --- a/src/accounts/accountsReducer.js +++ b/src/accounts/accountsReducer.js @@ -1,4 +1,4 @@ -import { ACCOUNTS_FETCHED, ACCOUNTS_FETCHING } from './accountsActions' +import { ACCOUNTS_CHANGED, ACCOUNTS_FETCHED, ACCOUNTS_FETCHING } from './accountsActions' const initialState = {} @@ -7,7 +7,7 @@ const accountsReducer = (state = initialState, action) => { return state } - if (action.type === ACCOUNTS_FETCHED) { + if (action.type === ACCOUNTS_FETCHED || action.type === ACCOUNTS_CHANGED) { return Object.assign({}, state, action.accounts) } diff --git a/src/accounts/accountsSaga.js b/src/accounts/accountsSaga.js index 4665fd5..15da128 100644 --- a/src/accounts/accountsSaga.js +++ b/src/accounts/accountsSaga.js @@ -9,10 +9,10 @@ export function * getAccounts (action) { try { yield put({ type: ACCOUNTS_FETCHING }); - const accounts = yield call(web3.eth.getAccounts) + const accounts = yield call(web3.eth.getAccounts); - if (!accounts) - throw 'No accounts found!' + if (!accounts.length) + throw new Error('No accounts found!'); yield put({ type: ACCOUNTS_FETCHED, accounts }) } catch (error) { diff --git a/src/contracts/constants.js b/src/contracts/constants.js index 54d4f54..58f51b8 100644 --- a/src/contracts/constants.js +++ b/src/contracts/constants.js @@ -1,7 +1,7 @@ -export const EVENT_FIRED = 'EVENT_FIRED' -export const EVENT_CHANGED = 'EVENT_CHANGED' -export const EVENT_ERROR = 'EVENT_ERROR' -export const LISTEN_FOR_EVENT = 'LISTEN_FOR_EVENT' +export const CONTRACT_EVENT_FIRED = 'CONTRACT_EVENT_FIRED' +export const CONTRACT_EVENT_CHANGED = 'CONTRACT_EVENT_CHANGED' +export const CONTRACT_EVENT_ERROR = 'CONTRACT_EVENT_ERROR' +export const CONTRACT_EVENT_LISTEN = 'CONTRACT_EVENT_LISTEN' export const CONTRACT_INITIALIZING = 'CONTRACT_INITIALIZING' export const CONTRACT_INITIALIZED = 'CONTRACT_INITIALIZED' export const CONTRACT_NOT_DEPLOYED = 'CONTRACT_NOT_DEPLOYED' diff --git a/src/contracts/contractsReducer.js b/src/contracts/contractsReducer.js index 540ded4..a075c53 100644 --- a/src/contracts/contractsReducer.js +++ b/src/contracts/contractsReducer.js @@ -123,7 +123,7 @@ const contractsReducer = (state = initialState, action) => { * Contract Events */ - if (action.type === ContractActions.EVENT_FIRED) { + if (action.type === ContractActions.CONTRACT_EVENT_FIRED) { return { ...state, [action.name]: { diff --git a/src/contracts/contractsSaga.js b/src/contracts/contractsSaga.js index d50d342..12a927f 100644 --- a/src/contracts/contractsSaga.js +++ b/src/contracts/contractsSaga.js @@ -16,13 +16,13 @@ export function createContractEventChannel ({ return eventChannel(emit => { const eventListener = contract.events[eventName](eventOptions) .on('data', event => { - emit({ type: ContractActions.EVENT_FIRED, name, event }) + emit({ type: ContractActions.CONTRACT_EVENT_FIRED, name, event }) }) .on('changed', event => { - emit({ type: ContractActions.EVENT_CHANGED, name, event }) + emit({ type: ContractActions.CONTRACT_EVENT_CHANGED, name, event }) }) .on('error', error => { - emit({ type: ContractActions.EVENT_ERROR, name, error }) + emit({ type: ContractActions.CONTRACT_EVENT_ERROR, name, error }) emit(END) }) @@ -287,7 +287,7 @@ function * contractsSaga () { yield takeEvery(ContractActions.SEND_CONTRACT_TX, callSendContractTx) yield takeEvery(ContractActions.CALL_CONTRACT_FN, callCallContractFn) yield takeEvery(ContractActions.CONTRACT_SYNCING, callSyncContract) - yield takeEvery(ContractActions.LISTEN_FOR_EVENT, callListenForContractEvent) + yield takeEvery(ContractActions.CONTRACT_EVENT_LISTEN, callListenForContractEvent) } export default contractsSaga diff --git a/src/defaultOptions.js b/src/defaultOptions.js index ed10f3e..e157670 100644 --- a/src/defaultOptions.js +++ b/src/defaultOptions.js @@ -9,6 +9,8 @@ const defaultOptions = { contracts: [], events: {}, syncAlways: false, + reloadWindowOnNetworkChange: false, + reloadWindowOnAccountChange: false, networkWhitelist: [] } diff --git a/src/drizzleStatus/drizzleActions.js b/src/drizzle/drizzleActions.js similarity index 100% rename from src/drizzleStatus/drizzleActions.js rename to src/drizzle/drizzleActions.js diff --git a/src/drizzle-middleware.js b/src/drizzle/drizzleMiddleware.js similarity index 59% rename from src/drizzle-middleware.js rename to src/drizzle/drizzleMiddleware.js index 0718af2..e398042 100644 --- a/src/drizzle-middleware.js +++ b/src/drizzle/drizzleMiddleware.js @@ -1,6 +1,7 @@ -import * as DrizzleActions from './drizzleStatus/drizzleActions' -import * as ContractActions from './contracts/constants' -import { ACCOUNTS_FETCHED } from './accounts/accountsActions' +import * as DrizzleActions from './drizzleActions' +import * as ContractActions from '../contracts/constants' +import { ACCOUNTS_CHANGED, ACCOUNTS_FETCHED } from '../accounts/accountsActions' +import { WEB3_NETWORK_CHANGED } from '../web3/web3Actions' export const drizzleMiddleware = drizzleInstance => store => next => action => { const { type } = action @@ -9,6 +10,23 @@ export const drizzleMiddleware = drizzleInstance => store => next => action => { drizzleInstance = action.drizzle } + // If network changes, drizzle should reinitialize + if (type === WEB3_NETWORK_CHANGED) { + // Hard reinitialization + if(drizzleInstance.options.reloadWindowOnNetworkChange) + window.location.reload(); + else{ // Soft reinitialization + store.dispatch({ + type: DrizzleActions.DRIZZLE_INITIALIZING, + drizzle: drizzleInstance, + options: drizzleInstance.options + }) + } + } + + if (type === ACCOUNTS_CHANGED && drizzleInstance.options.reloadWindowOnAccountChange) + window.location.reload(); + if ( type === ACCOUNTS_FETCHED && drizzleInstance && @@ -40,8 +58,8 @@ export const drizzleMiddleware = drizzleInstance => store => next => action => { } store.dispatch(notificationAction) - // Don't propogate current action - return + // Don't propagate current action + return; } } return next(action) diff --git a/src/drizzleStatus/drizzleStatusReducer.js b/src/drizzle/drizzleStatusReducer.js similarity index 100% rename from src/drizzleStatus/drizzleStatusReducer.js rename to src/drizzle/drizzleStatusReducer.js diff --git a/src/drizzleStatus/drizzleStatusSaga.js b/src/drizzle/drizzleStatusSaga.js similarity index 90% rename from src/drizzleStatus/drizzleStatusSaga.js rename to src/drizzle/drizzleStatusSaga.js index 7879f5e..1a71857 100644 --- a/src/drizzleStatus/drizzleStatusSaga.js +++ b/src/drizzle/drizzleStatusSaga.js @@ -1,13 +1,13 @@ import { call, put, takeLatest } from 'redux-saga/effects' // Initialization Functions -import { getNetworkId, initializeWeb3 } from '../web3/web3Saga' +import { getNetworkInfo, initializeWeb3 } from '../web3/web3Saga' import { getAccounts } from '../accounts/accountsSaga' import { getAccountBalances } from '../accountBalances/accountBalancesSaga' import * as DrizzleActions from './drizzleActions' import * as BlocksActions from '../blocks/blockActions' -import { NETWORK_IDS, NETWORK_MISMATCH } from '../web3/web3Actions' +import { NETWORK_IDS, WEB3_NETWORK_MISMATCH } from '../web3/web3Actions' import { CONTRACT_NOT_DEPLOYED } from '../contracts/constants' import { isContractDeployed } from '../contracts/contractsSaga' @@ -23,14 +23,14 @@ export function * initializeDrizzle (action) { // further web3 interaction, and note web3 will be undefined // if (web3) { - const networkId = yield call(getNetworkId, { web3 }) + const networkId = yield call(getNetworkInfo, { web3 }) // Check whether network is allowed const networkWhitelist = options.networkWhitelist if (networkWhitelist.length && networkId !== NETWORK_IDS.ganache && !networkWhitelist.includes(networkId)) { - yield put({ type: NETWORK_MISMATCH, networkId }) + yield put({ type: WEB3_NETWORK_MISMATCH, networkId }) } else { // Get initial accounts list and balances. yield call(getAccounts, { web3 }) diff --git a/src/generateStore.js b/src/generateStore.js index 603b364..f39feed 100644 --- a/src/generateStore.js +++ b/src/generateStore.js @@ -1,10 +1,10 @@ import { all, fork } from 'redux-saga/effects' import { applyMiddleware, combineReducers, compose, createStore } from 'redux' import createSagaMiddleware from 'redux-saga' -import drizzleSagas from './rootSaga' -import drizzleReducers from './reducer' +import drizzleSagas from './root/rootSaga' +import drizzleReducers from './root/rootReducer' import { generateContractsInitialState } from './contractStateUtils' -import drizzleMW from './drizzle-middleware' +import drizzleMiddlewares from './root/rootMiddleware' const composeSagas = sagas => function * () { @@ -28,7 +28,7 @@ export function generateStore ({ drizzleOptions, appReducers = {}, appSagas = [], - appMiddlewares = [], + appMiddlewares = drizzleMiddlewares, disableReduxDevTools = false, ...options }) { @@ -55,7 +55,7 @@ export function generateStore ({ } const sagaMiddleware = createSagaMiddleware() - const allMiddlewares = [...appMiddlewares, sagaMiddleware, drizzleMW] + const allMiddlewares = [...appMiddlewares, sagaMiddleware] const allReducers = { ...drizzleReducers, ...appReducers } const store = createStore( diff --git a/src/index.js b/src/index.js index 1f48a64..06f3d56 100644 --- a/src/index.js +++ b/src/index.js @@ -7,23 +7,13 @@ import * as EventActions from './contracts/constants' import * as AccountActions from './accounts/accountsActions' // Reducers -import drizzleReducers from './reducer' +import drizzleReducers from './root/rootReducer' -// Middleware -import drizzleMiddleware from './drizzle-middleware' -import accountsMiddleware from './accounts/accountsMiddleware' -import accountBalancesMiddleware from './accountBalances/accountBalancesMiddleware' -import web3Middleware from './web3/web3Middleware' +// Middlewares +import drizzleMiddlewares from './root/rootMiddleware' // Sagas -import drizzleSagas from './rootSaga' - -const drizzleMiddlewares = [ - drizzleMiddleware, - accountsMiddleware, - accountBalancesMiddleware, - web3Middleware -] +import drizzleSagas from './root/rootSaga' const drizzleActions = { account: AccountActions, diff --git a/src/reducer.js b/src/reducer.js deleted file mode 100644 index 0104422..0000000 --- a/src/reducer.js +++ /dev/null @@ -1,20 +0,0 @@ -import accountsReducer from './accounts/accountsReducer' -import accountBalancesReducer from './accountBalances/accountBalancesReducer' -import blocksReducer from './blocks/blocksReducer' -import contractsReducer from './contracts/contractsReducer' -import drizzleStatusReducer from './drizzleStatus/drizzleStatusReducer' -import transactionsReducer from './transactions/transactionsReducer' -import transactionStackReducer from './transactions/transactionStackReducer' -import web3Reducer from './web3/web3Reducer' - -// All our reducers -export default { - accounts: accountsReducer, - accountBalances: accountBalancesReducer, - contracts: contractsReducer, - currentBlock: blocksReducer, - drizzleStatus: drizzleStatusReducer, - transactions: transactionsReducer, - transactionStack: transactionStackReducer, - web3: web3Reducer -} diff --git a/src/root/rootMiddleware.js b/src/root/rootMiddleware.js new file mode 100644 index 0000000..fa144f9 --- /dev/null +++ b/src/root/rootMiddleware.js @@ -0,0 +1,11 @@ +import drizzleMiddleware from '../drizzle/drizzleMiddleware' +import accountsMiddleware from '../accounts/accountsMiddleware' +import accountBalancesMiddleware from '../accountBalances/accountBalancesMiddleware' +import web3Middleware from '../web3/web3Middleware' + +export default [ + drizzleMiddleware, + accountsMiddleware, + accountBalancesMiddleware, + web3Middleware +] diff --git a/src/root/rootReducer.js b/src/root/rootReducer.js new file mode 100644 index 0000000..3719b7f --- /dev/null +++ b/src/root/rootReducer.js @@ -0,0 +1,20 @@ +import accountsReducer from '../accounts/accountsReducer' +import accountBalancesReducer from '../accountBalances/accountBalancesReducer' +import blocksReducer from '../blocks/blocksReducer' +import contractsReducer from '../contracts/contractsReducer' +import drizzleStatusReducer from '../drizzle/drizzleStatusReducer' +import transactionsReducer from '../transactions/transactionsReducer' +import transactionStackReducer from '../transactions/transactionStackReducer' +import web3Reducer from '../web3/web3Reducer' + +// All our reducers +export default { + accounts: accountsReducer, + accountBalances: accountBalancesReducer, + contracts: contractsReducer, + currentBlock: blocksReducer, + drizzleStatus: drizzleStatusReducer, + transactions: transactionsReducer, + transactionStack: transactionStackReducer, + web3: web3Reducer +} diff --git a/src/root/rootSaga.js b/src/root/rootSaga.js new file mode 100644 index 0000000..22bc2b0 --- /dev/null +++ b/src/root/rootSaga.js @@ -0,0 +1,13 @@ +import accountBalancesSaga from '../accountBalances/accountBalancesSaga' +import blocksSaga from '../blocks/blocksSaga' +import contractsSaga from '../contracts/contractsSaga' +import drizzleStatusSaga from '../drizzle/drizzleStatusSaga' +import web3Saga from '../web3/web3Saga' + +export default [ + accountBalancesSaga, + blocksSaga, + contractsSaga, + drizzleStatusSaga, + web3Saga +] diff --git a/src/rootSaga.js b/src/rootSaga.js deleted file mode 100644 index d165edc..0000000 --- a/src/rootSaga.js +++ /dev/null @@ -1,11 +0,0 @@ -import accountBalancesSaga from './accountBalances/accountBalancesSaga' -import blocksSaga from './blocks/blocksSaga' -import contractsSaga from './contracts/contractsSaga' -import drizzleStatusSaga from './drizzleStatus/drizzleStatusSaga' - -export default [ - accountBalancesSaga, - blocksSaga, - contractsSaga, - drizzleStatusSaga -] diff --git a/src/web3/web3Actions.js b/src/web3/web3Actions.js index 6272715..c56259f 100644 --- a/src/web3/web3Actions.js +++ b/src/web3/web3Actions.js @@ -3,10 +3,11 @@ export const WEB3_INITIALIZED = 'WEB3_INITIALIZED' export const WEB3_FAILED = 'WEB3_FAILED' export const WEB3_USER_DENIED = 'WEB3_USER_DENIED' -export const NETWORK_ID_FETCHED = 'NETWORK_ID_FETCHED' -export const NETWORK_ID_CHANGED = 'NETWORK_ID_CHANGED' -export const NETWORK_ID_FAILED = 'NETWORK_ID_FAILED' -export const NETWORK_MISMATCH = 'NETWORK_MISMATCH' +export const WEB3_NETWORK_FETCHING = 'WEB3_NETWORK_FETCHING' +export const WEB3_NETWORK_FETCHED = 'WEB3_NETWORK_FETCHED' +export const WEB3_NETWORK_CHANGED = 'WEB3_NETWORK_CHANGED' +export const WEB3_NETWORK_FAILED = 'WEB3_NETWORK_FAILED' +export const WEB3_NETWORK_MISMATCH = 'WEB3_NETWORK_MISMATCH' export const NETWORK_IDS = { mainnet: 1, @@ -17,9 +18,15 @@ export const NETWORK_IDS = { ganache: 5777 } -export function networkIdChanged (web3, networkId) { +export function networkInfoFetching (web3) { return { - type: NETWORK_ID_CHANGED, - networkId + type: WEB3_NETWORK_FETCHING, + web3 + } +} + +export function networkChanged () { + return { + type: WEB3_NETWORK_CHANGED } } diff --git a/src/web3/web3Middleware.js b/src/web3/web3Middleware.js index 43f1dd4..abb2636 100644 --- a/src/web3/web3Middleware.js +++ b/src/web3/web3Middleware.js @@ -1,18 +1,18 @@ -import { networkIdChanged, WEB3_INITIALIZED } from './web3Actions' +import { networkChanged, networkInfoFetching, WEB3_INITIALIZED } from './web3Actions' -export const web3Middleware = () => store => next => action => { +export const web3Middleware = web3 => store => next => action => { const { type } = action if (type === WEB3_INITIALIZED) { if(!window.ethereum) console.warn('No Metamask detected, not subscribed to network changes!') else { - window.ethereum.on('networkChanged', (networkId) => { - // Warning: 'networkChanged' is deprecated (EIP-1193) - const storedNetworkId = store.getState().web3.networkId; - if(storedNetworkId && (networkId !== storedNetworkId)){ - store.dispatch(networkIdChanged(networkId)); // Just to be typical - window.location.reload(); + web3 = action.web3; + window.ethereum.on('chainChanged', (chainId) => { + const storedNetworkId = store.getState().web3.chainId; + if(storedNetworkId && (chainId !== storedNetworkId)){ + store.dispatch(networkChanged()); + store.dispatch(networkInfoFetching(web3)); } }); } @@ -20,5 +20,5 @@ export const web3Middleware = () => store => next => action => { return next(action) } -const initializedMiddleware = web3Middleware() +const initializedMiddleware = web3Middleware(undefined) export default initializedMiddleware diff --git a/src/web3/web3Reducer.js b/src/web3/web3Reducer.js index b81c50a..c0fc39f 100644 --- a/src/web3/web3Reducer.js +++ b/src/web3/web3Reducer.js @@ -33,21 +33,22 @@ const web3Reducer = (state = initialState, action) => { } } - if (action.type === Action.NETWORK_ID_FETCHED - || action.type === Action.NETWORK_ID_CHANGED) { + if (action.type === Action.WEB3_NETWORK_FETCHED) { return { ...state, - networkId: action.networkId + networkId: action.networkInfo.networkId, + chainId: action.networkInfo.chainId, + nodeInfo: action.networkInfo.nodeInfo } } - if (action.type === Action.NETWORK_ID_FAILED) { + if (action.type === Action.WEB3_NETWORK_FAILED) { return { ...state, networkId: action.networkId } } - if (action.type === Action.NETWORK_MISMATCH) { + if (action.type === Action.WEB3_NETWORK_MISMATCH) { return { ...state, networkMismatch: true diff --git a/src/web3/web3Saga.js b/src/web3/web3Saga.js index 0e496b0..c9ffe5a 100644 --- a/src/web3/web3Saga.js +++ b/src/web3/web3Saga.js @@ -1,4 +1,4 @@ -import { call, put } from 'redux-saga/effects' +import { call, put, takeLatest } from 'redux-saga/effects' import * as Action from './web3Actions' const Web3 = require('web3'); @@ -66,19 +66,30 @@ export function * initializeWeb3 (options) { } /* - * Fetch Network ID + * Fetch Network Information */ -export function * getNetworkId ({ web3 }) { +export function * getNetworkInfo ({ web3 }) { try { const networkId = yield call(web3.eth.net.getId); + const chainId = yield call(web3.eth.getChainId); + const nodeInfo = yield call(web3.eth.getNodeInfo); - yield put({ type: Action.NETWORK_ID_FETCHED, networkId }); + const networkInfo = { networkId, chainId, nodeInfo }; - return networkId + yield put({ type: Action.WEB3_NETWORK_FETCHED, networkInfo }); + + return networkInfo; } catch (error) { - yield put({ type: Action.NETWORK_ID_FAILED, error }); + yield put({ type: Action.WEB3_NETWORK_FAILED, error }); - console.error('Error fetching network ID:'); + console.error('Error fetching network information:'); console.error(error); } } + +function * web3Saga () { + yield takeLatest(Action.WEB3_NETWORK_FETCHING, getNetworkInfo); +} + +export default web3Saga; +