Assist.js
Takes care of onboarding your users, keeping them informed about
transaction status and comprehensive usage analytics with minimal
setup. Supports web3.js
versions 0.20 and 1.0.
note: web3.js
1.0.0 beta versions 38, 39, 40, 41, 42, 43, 44, 45 have bugs when interacting with MetaMask, we recommend you avoid these versions of web3.js
Preview
☝️ A collection of Assist's UI elements.
👇 Assist's transaction notifications in action.
Getting Started
To integrate Assist.js into your dapp, you'll need to do 5 things:
- Create a free account and get an API key from account.blocknative.com
- Install the widget
- Initialize the library
- Call
onboard
- Decorate your contracts
Install the widget
npm
npm i bnc-assist
Yarn
yarn add bnc-assist
Script Tag
The library uses semantic versioning.
The current version is 0.7.2.
There are minified and non-minified versions.
Put this script at the top of your <head>
<script src="https://assist.blocknative.com/0-7-2/assist.js"></script>
<script src="https://assist.blocknative.com/0-7-2/assist.min.js"></script>
Initialize the Library
Full documentation of the config
object is below, but the minimum required config
is as follows:
var bncAssistConfig = {
dappId: apiKey,
networkId: networkId
};
var assistInstance = assist.init(bncAssistConfig);
Call onboard
At some point in your dapp's workflow, you'll want to ensure users are within an environment which
will allow them to make transactions, such as a browser with MetaMask, unlocked wallet, etc.
This is done by calling onboard
. Some dapps might want to call onboard
immediately upon any page
load. Others may wait until loading certain pages or until a certain button is clicked.
In any event, it is as simple as calling:
assistInstance.onboard()
.then(function(state) {
})
.catch(function(state) {
})
Decorate Your Contracts
The first three steps in the getting started flow will get your users onboarded. This step adds
transaction support in order to help guide your users through a series of issues that can arise
when signing transactions.
Using our decorated contracts will also enable some anonymized transaction-level metrics to give
you insights into things including but not limited to:
- How many transactions fail because a user doesn't have enough Ether
- How many transactions are started but rejected by the user
- How many users come to your dapp without a web3 wallet
Decorating your contracts is simple:
var myContract = new web3.eth.Contract(abi, address)
var myDecoratedContract = assistInstance.Contract(myContract)
You can then use myDecoratedContract
instead of myContract
.
To speed things up, you can decorate the contract inline:
var myContract = assistInstance.Contract(new web3.eth.Contract(abi, address))
API Reference
Config
A JavaScript Object that is passed to the init
function. Default values are in [square brackets] where they are set by Assist.js.
var config = {
networkId: Number,
dappId: String,
web3: Object,
mobileBlocked: Boolean,
minimumBalance: String,
headlessMode: Boolean,
messages: {
txRequest: Function,
txSent: Function,
txPending: Function,
txSendFail: Function,
txStall: Function,
txFailed: Function,
nsfFail: Function,
txRepeat: Function,
txAwaitingApproval: Function,
txConfirmReminder: Function,
txConfirmed: Function,
txSpeedUp: Function
},
images: {
welcome: {
src: String,
srcset: String
},
complete: {
src: String,
srcset: String
}
},
style: {
darkMode: Boolean,
notificationsPosition: String,
css: String
},
truffleContract: Boolean,
}
Custom Transaction Messages
Custom transaction messages can be set to override the default messages Assist
provides. To do this you provide callback functions for each eventCode
that you want to override. The callback functions must return a String
and will be called with the following object to provide context information about the transaction:
{
transaction: {
to: String,
gas: String,
gasPrice: String,
hash: String,
nonce: Number,
value: String
},
contract: {
methodName: String,
parameters: Array
}
}
You can provide a messages
object to the config
to set global message overrides. Each callback can parse the context object that is passed to it and decide what to return or just return a standard message for each eventCode
:
var config = {
messages: {
txSent: function(data) {
return 'Your transaction has been sent to the network'
},
txConfirmed: function(data) {
if (data.contract.methodName === 'contribute') {
return 'Congratulations! You are now a contributor to the campaign'
}
}
}
}
Sometimes you want more granular control over the transaction messages and you have all the relevant information you need to create a custom transaction message at the time of calling the method. In that case you can also add custom transactions messages inline with your transaction calls which take precedent over the messages set globally in the config.
Example
myContract.vote(param1, param2, options, callback, {messages: {txPending: () => `Voting for ${param1} in progress`}})
myContract.vote(param1, param2).send(options, {messages: {txPending: () => `Voting for ${param1} in progress`}})
The messages
object must always be the last argument provided to the send method for it to be recognized.
Ethereum Network Ids
The available ids for the networkId
property of the config object:
1
: mainnet3
: ropsten testnet4
: rinkeby testnet
The kovan testnet is not supported.
Local Networks
When you are running locally (e.g. using ganache), set networkId
in the config to the network id that the local network is set to. Any number that is not 1
, 3
, 4
and 42
is valid and will be recognized as a local network. If using the Ganache CLI you can set the network id via the --networkId
option.
State
Assist
keeps track of the current state of the user environment as a JavaScript Object
state = {
mobileDevice: Boolean,
validBrowser: Boolean,
currentProvider: String,
web3Wallet: Boolean,
accessToAccounts: Boolean,
walletLoggedIn: Boolean,
walletEnabled: Boolean,
accountAddress: String,
accountBalance: String,
minimumBalance: String,
userCurrentNetworkId: Number,
correctNetwork: Boolean,
}
The promises that are returned from calls to getState
and onboard
resolve and reject with this state
object.
Errors
All errors are called with eventCode
and message
properties.
Example
{
eventCode: 'initFail',
message: 'An API key is required to run Assist'
}
Error Codes
The following are the possible error codes from Assist.js.
initFail - initialization of the library failed
mobileBlocked - mobile browsers are blocked from accessing this dapp
browserFail - browser is not compatible with web3.js wallets
walletFail - user does not have a web3-enabled wallet installed
walletEnableFail - user has not logged into their wallet
networkFail - user's web3 wallet is not connected to the correct network
nsfFail - user does not have enough funds in their wallet
Headless Mode
By default, Assist will create UI elements in your application at certain times to guide users. You can disable this feature and run Assist in "headless mode" by setting headlessMode: true
in the config. This still enables you to collect analytics, but won't change the underlying behaviour of your application at all.
Mobile Dapps
Assist doesn't currently support mobile dapp browsers. If your dapp also doesn't support mobile browsers, setting mobileBlocked: true
in the config will detect mobile user agents and show UI that will direct them to use a desktop browser instead. If your dapp does support mobile devices then Assist will be disabled and your transactions and contracts will work as normal. However if you call the onboard
function when a user is on a mobile device, Assist will show a mobile not supported UI as onboarding isn't supported on mobile. So it is advised to check if a user is on a mobile device before calling onboard
. Calling getState
and referring to the mobileDevice
property is an easy way of doing that.
Minimum Balance
By supplying an amount of wei to the minimumBalance
option of the config, developers can limit access to their dapp to users who have at least this much Ether in their wallet.
Repeat Transactions
Assist will detect transactions which look to be repeated. We notify users of repeat transactions when we see sequential transactions with the same to
address and the same value
.
API
init(config)
Parameters
config
- Object
: Config object to configure and setup Assist (Required)
Returns
The initialized version of the Assist library
Example
var assistInstance = assist.init(assistConfig)
onboard()
Returns
Promise
- resolves with
state
object - rejects with
state
object
Example
assistInstance.onboard()
.then(function(state) {
})
.catch(function(state) {
})
Contract(contractInstance)
Parameters
contractInstance
- Object
: Instantiated web3 contract
object (Required)
Returns
A decorated contract
to be used instead of the original instance
Example
const myContract = new web3.eth.Contract(abi, address)
const myDecoratedContract = assistInstance.Contract(myContract)
mydecoratedContract.myMethod().call()
Transaction(txObject [, callback])
Parameters
txObject
- Object
: Transaction object (Required)
callback
- Function
: Optional error first style callback if you don't want to use promises
Returns
Promise
or PromiEvent
(web3.js 1.0
)
- resolves with transaction hash
- rejects with an error message
Example
assistInstance.Transaction(txObject)
.then(txHash => {
})
.catch(error => {
console.log(error.message)
})
getState()
Returns
Promise
- resolves with the
state
object that represents the current user environment
Example
assistInstance.getState()
.then(function(state) {
if (state.validBrowser) {
console.log('valid browser')
}
})
updateStyle(style)
Parameters
style
- Object
: Object containing new style information (Required)
const style = {
darkMode: Boolean,
css: String,
notificationsPosition: String,
}
Examples
const style = {
darkMode: true
}
assistInstance.updateStyle(style)
const style = {
darkMode: false,
css: `.bn-notification { background: black }`
}
assistInstance.updateStyle(style)
notify(type, message, options)
Trigger a custom UI notification
Parameters
type
- String
: One of: ['success', 'pending', 'error'] (Required)
message
- String
: The message to display in the notification. HTML can be embedded in the string. (Required)
options
- Object
: Further customize the notification
options = {
customTimeout: Number,
customCode: String
}
options.customTimeout defaults: { success: 2000, pending: 5000, error: 5000 }
Returns
Function
- a function that when called will dismiss the notification
Examples
assistInstance.notify('success', 'Operation was a success! Click <a href="https://example.com" target="_blank">here</a> to view more', { customTimeout: 5000 });
const dismiss = assistInstance.notify('pending', 'Loading data...', { customTimeout: -1 });
myEventEmitter.emit('fetch-data-from-backend')
myEventEmitter.on('data-from-backend-loaded', () => {
dismiss()
})
Contribute
Installing Dependencies
npm
npm i
Yarn
yarn
Tests
npm
npm test
Yarn
yarn test
Building
npm
npm run build
Yarn
yarn build