diff --git a/src/__integration-tests__/ui-rendering/event-definitions.js b/src/__integration-tests__/ui-rendering/event-definitions.js
index 356f8810..8a5e64e3 100644
--- a/src/__integration-tests__/ui-rendering/event-definitions.js
+++ b/src/__integration-tests__/ui-rendering/event-definitions.js
@@ -225,13 +225,29 @@ export default {
{ config: { messages: { txSent: () => 'txSent custom msg' }, style: {} } }
]
},
- txStall: {
+ txStallPending: {
categories: ['activeTransaction', 'activeContract'],
params: { transaction: mockTxFactory({ nonce: true, startTime: true }) },
customStates: [
initialState,
{
- config: { messages: { txStall: () => 'txStall custom msg' }, style: {} }
+ config: {
+ messages: { txStallPending: () => 'txStall custom msg' },
+ style: {}
+ }
+ }
+ ]
+ },
+ txStallConfirmed: {
+ categories: ['activeTransaction', 'activeContract'],
+ params: { transaction: mockTxFactory({ nonce: true, startTime: true }) },
+ customStates: [
+ initialState,
+ {
+ config: {
+ messages: { txStallConfirmed: () => 'txStall custom msg' },
+ style: {}
+ }
}
]
},
diff --git a/src/__tests__/js/contract/__snapshots__/index.test.js.snap b/src/__tests__/js/contract/__snapshots__/index.test.js.snap
index 63329de3..7e9cde95 100644
--- a/src/__tests__/js/contract/__snapshots__/index.test.js.snap
+++ b/src/__tests__/js/contract/__snapshots__/index.test.js.snap
@@ -10721,3 +10721,1331 @@ Object {
},
}
`;
+
+exports[`using web3 1.2.0 Contract is called with a truffle contract it doesn't fail and returns the expected decorated contract 1`] = `
+Object {
+ "BatchRequest": undefined,
+ "_jsonInterface": undefined,
+ "abiModel": undefined,
+ "events": Object {
+ "contract": null,
+ },
+ "givenProvider": undefined,
+ "methods": Object {
+ "convert(uint256,uint256)": [Function],
+ "subtract(uint256,uint256)": [Function],
+ },
+ "options": undefined,
+}
+`;
+
+exports[`using web3 1.2.0 Contract is called with a web3 contract it doesn't fail and returns the expected decorated contract 1`] = `
+Object {
+ "BatchRequest": [Function],
+ "_jsonInterface": Array [
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "name",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bytes32",
+ },
+ ],
+ "payable": false,
+ "signature": "0x06fdde03",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [],
+ "name": "stop",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x07da68f5",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "approve",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0x095ea7b3",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "owner_",
+ "type": "address",
+ },
+ ],
+ "name": "setOwner",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x13af4035",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "totalSupply",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "uint256",
+ },
+ ],
+ "payable": false,
+ "signature": "0x18160ddd",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "transferFrom",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0x23b872dd",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "decimals",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "uint256",
+ },
+ ],
+ "payable": false,
+ "signature": "0x313ce567",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "mint",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x40c10f19",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "burn",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x42966c68",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "name_",
+ "type": "bytes32",
+ },
+ ],
+ "name": "setName",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x5ac801fe",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ ],
+ "name": "balanceOf",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "uint256",
+ },
+ ],
+ "payable": false,
+ "signature": "0x70a08231",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "stopped",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0x75f12b21",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "authority_",
+ "type": "address",
+ },
+ ],
+ "name": "setAuthority",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x7a9e5e4b",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "owner",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "address",
+ },
+ ],
+ "payable": false,
+ "signature": "0x8da5cb5b",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "symbol",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bytes32",
+ },
+ ],
+ "payable": false,
+ "signature": "0x95d89b41",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "burn",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x9dc29fac",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "mint",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xa0712d68",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "transfer",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0xa9059cbb",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "push",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xb753a98c",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "move",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xbb35783b",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [],
+ "name": "start",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xbe9a6555",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "authority",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "address",
+ },
+ ],
+ "payable": false,
+ "signature": "0xbf7e214f",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ ],
+ "name": "approve",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0xdaea85c5",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ ],
+ "name": "allowance",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "uint256",
+ },
+ ],
+ "payable": false,
+ "signature": "0xdd62ed3e",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "pull",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xf2d5d56b",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "name": "symbol_",
+ "type": "bytes32",
+ },
+ ],
+ "payable": false,
+ "stateMutability": "nonpayable",
+ "type": "constructor",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "Mint",
+ "payable": undefined,
+ "signature": "0x0f6798a560793a54c3bcfe86a93cde1e73087d944c0ea20544137d4121396885",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "Burn",
+ "payable": undefined,
+ "signature": "0xcc16f5dbb4873280815c1ee09dbd06736cffcc184412cf7a71a0fdb75d397ca5",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "authority",
+ "type": "address",
+ },
+ ],
+ "name": "LogSetAuthority",
+ "payable": undefined,
+ "signature": "0x1abebea81bfa2637f28358c371278fb15ede7ea8dd28d2e03b112ff6d936ada4",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "owner",
+ "type": "address",
+ },
+ ],
+ "name": "LogSetOwner",
+ "payable": undefined,
+ "signature": "0xce241d7ca1f669fee44b6fc00b8eba2df3bb514eed0f6f668f8f89096e81ed94",
+ "type": "event",
+ },
+ Object {
+ "anonymous": true,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "sig",
+ "type": "bytes4",
+ },
+ Object {
+ "indexed": true,
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "indexed": true,
+ "name": "foo",
+ "type": "bytes32",
+ },
+ Object {
+ "indexed": true,
+ "name": "bar",
+ "type": "bytes32",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ Object {
+ "indexed": false,
+ "name": "fax",
+ "type": "bytes",
+ },
+ ],
+ "name": "LogNote",
+ "payable": undefined,
+ "signature": "0x644843f351d3fba4abcd60109eaff9f54bac8fb8ccf0bab941009c21df21cf31",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "indexed": true,
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "Approval",
+ "payable": undefined,
+ "signature": "0x8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "indexed": true,
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "Transfer",
+ "payable": undefined,
+ "signature": "0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef",
+ "type": "event",
+ },
+ ],
+ "abiModel": undefined,
+ "events": Object {
+ "0x0f6798a560793a54c3bcfe86a93cde1e73087d944c0ea20544137d4121396885": [Function],
+ "0x1abebea81bfa2637f28358c371278fb15ede7ea8dd28d2e03b112ff6d936ada4": [Function],
+ "0x644843f351d3fba4abcd60109eaff9f54bac8fb8ccf0bab941009c21df21cf31": [Function],
+ "0x8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925": [Function],
+ "0xcc16f5dbb4873280815c1ee09dbd06736cffcc184412cf7a71a0fdb75d397ca5": [Function],
+ "0xce241d7ca1f669fee44b6fc00b8eba2df3bb514eed0f6f668f8f89096e81ed94": [Function],
+ "0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef": [Function],
+ "Approval": [Function],
+ "Approval(address,address,uint256)": [Function],
+ "Burn": [Function],
+ "Burn(address,uint256)": [Function],
+ "LogNote": [Function],
+ "LogNote(bytes4,address,bytes32,bytes32,uint256,bytes)": [Function],
+ "LogSetAuthority": [Function],
+ "LogSetAuthority(address)": [Function],
+ "LogSetOwner": [Function],
+ "LogSetOwner(address)": [Function],
+ "Mint": [Function],
+ "Mint(address,uint256)": [Function],
+ "Transfer": [Function],
+ "Transfer(address,address,uint256)": [Function],
+ "allEvents": [Function],
+ "contract": null,
+ },
+ "givenProvider": null,
+ "methods": Object {
+ "allowance": [Function],
+ "allowance(address,address)": [Function],
+ "approve": [Function],
+ "approve(address)": [Function],
+ "approve(address,uint256)": [Function],
+ "authority": [Function],
+ "authority()": [Function],
+ "balanceOf": [Function],
+ "balanceOf(address)": [Function],
+ "burn": [Function],
+ "burn(address,uint256)": [Function],
+ "burn(uint256)": [Function],
+ "decimals": [Function],
+ "decimals()": [Function],
+ "mint": [Function],
+ "mint(address,uint256)": [Function],
+ "mint(uint256)": [Function],
+ "move": [Function],
+ "move(address,address,uint256)": [Function],
+ "name": [Function],
+ "name()": [Function],
+ "owner": [Function],
+ "owner()": [Function],
+ "pull": [Function],
+ "pull(address,uint256)": [Function],
+ "push": [Function],
+ "push(address,uint256)": [Function],
+ "setAuthority": [Function],
+ "setAuthority(address)": [Function],
+ "setName": [Function],
+ "setName(bytes32)": [Function],
+ "setOwner": [Function],
+ "setOwner(address)": [Function],
+ "start": [Function],
+ "start()": [Function],
+ "stop": [Function],
+ "stop()": [Function],
+ "stopped": [Function],
+ "stopped()": [Function],
+ "symbol": [Function],
+ "symbol()": [Function],
+ "totalSupply": [Function],
+ "totalSupply()": [Function],
+ "transfer": [Function],
+ "transfer(address,uint256)": [Function],
+ "transferFrom": [Function],
+ "transferFrom(address,address,uint256)": [Function],
+ },
+ "options": Object {
+ "address": "0x0000000000000000000000000000000000000000",
+ "jsonInterface": Array [
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "name",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bytes32",
+ },
+ ],
+ "payable": false,
+ "signature": "0x06fdde03",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [],
+ "name": "stop",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x07da68f5",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "approve",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0x095ea7b3",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "owner_",
+ "type": "address",
+ },
+ ],
+ "name": "setOwner",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x13af4035",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "totalSupply",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "uint256",
+ },
+ ],
+ "payable": false,
+ "signature": "0x18160ddd",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "transferFrom",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0x23b872dd",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "decimals",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "uint256",
+ },
+ ],
+ "payable": false,
+ "signature": "0x313ce567",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "mint",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x40c10f19",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "burn",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x42966c68",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "name_",
+ "type": "bytes32",
+ },
+ ],
+ "name": "setName",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x5ac801fe",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ ],
+ "name": "balanceOf",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "uint256",
+ },
+ ],
+ "payable": false,
+ "signature": "0x70a08231",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "stopped",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0x75f12b21",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "authority_",
+ "type": "address",
+ },
+ ],
+ "name": "setAuthority",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x7a9e5e4b",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "owner",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "address",
+ },
+ ],
+ "payable": false,
+ "signature": "0x8da5cb5b",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "symbol",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bytes32",
+ },
+ ],
+ "payable": false,
+ "signature": "0x95d89b41",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "burn",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0x9dc29fac",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "mint",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xa0712d68",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "transfer",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0xa9059cbb",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "push",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xb753a98c",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "move",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xbb35783b",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [],
+ "name": "start",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xbe9a6555",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [],
+ "name": "authority",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "address",
+ },
+ ],
+ "payable": false,
+ "signature": "0xbf7e214f",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ ],
+ "name": "approve",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "bool",
+ },
+ ],
+ "payable": false,
+ "signature": "0xdaea85c5",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": true,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "name": "guy",
+ "type": "address",
+ },
+ ],
+ "name": "allowance",
+ "outputs": Array [
+ Object {
+ "name": "",
+ "type": "uint256",
+ },
+ ],
+ "payable": false,
+ "signature": "0xdd62ed3e",
+ "stateMutability": "view",
+ "type": "function",
+ },
+ Object {
+ "constant": false,
+ "inputs": Array [
+ Object {
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "pull",
+ "outputs": Array [],
+ "payable": false,
+ "signature": "0xf2d5d56b",
+ "stateMutability": "nonpayable",
+ "type": "function",
+ },
+ Object {
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "name": "symbol_",
+ "type": "bytes32",
+ },
+ ],
+ "payable": false,
+ "stateMutability": "nonpayable",
+ "type": "constructor",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "Mint",
+ "payable": undefined,
+ "signature": "0x0f6798a560793a54c3bcfe86a93cde1e73087d944c0ea20544137d4121396885",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "Burn",
+ "payable": undefined,
+ "signature": "0xcc16f5dbb4873280815c1ee09dbd06736cffcc184412cf7a71a0fdb75d397ca5",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "authority",
+ "type": "address",
+ },
+ ],
+ "name": "LogSetAuthority",
+ "payable": undefined,
+ "signature": "0x1abebea81bfa2637f28358c371278fb15ede7ea8dd28d2e03b112ff6d936ada4",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "owner",
+ "type": "address",
+ },
+ ],
+ "name": "LogSetOwner",
+ "payable": undefined,
+ "signature": "0xce241d7ca1f669fee44b6fc00b8eba2df3bb514eed0f6f668f8f89096e81ed94",
+ "type": "event",
+ },
+ Object {
+ "anonymous": true,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "sig",
+ "type": "bytes4",
+ },
+ Object {
+ "indexed": true,
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "indexed": true,
+ "name": "foo",
+ "type": "bytes32",
+ },
+ Object {
+ "indexed": true,
+ "name": "bar",
+ "type": "bytes32",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ Object {
+ "indexed": false,
+ "name": "fax",
+ "type": "bytes",
+ },
+ ],
+ "name": "LogNote",
+ "payable": undefined,
+ "signature": "0x644843f351d3fba4abcd60109eaff9f54bac8fb8ccf0bab941009c21df21cf31",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "indexed": true,
+ "name": "guy",
+ "type": "address",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "Approval",
+ "payable": undefined,
+ "signature": "0x8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925",
+ "type": "event",
+ },
+ Object {
+ "anonymous": false,
+ "constant": undefined,
+ "inputs": Array [
+ Object {
+ "indexed": true,
+ "name": "src",
+ "type": "address",
+ },
+ Object {
+ "indexed": true,
+ "name": "dst",
+ "type": "address",
+ },
+ Object {
+ "indexed": false,
+ "name": "wad",
+ "type": "uint256",
+ },
+ ],
+ "name": "Transfer",
+ "payable": undefined,
+ "signature": "0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef",
+ "type": "event",
+ },
+ ],
+ },
+}
+`;
diff --git a/src/__tests__/js/contract/index.test.js b/src/__tests__/js/contract/index.test.js
index a31baace..96e7ece3 100644
--- a/src/__tests__/js/contract/index.test.js
+++ b/src/__tests__/js/contract/index.test.js
@@ -49,7 +49,7 @@ multidepRequire.forEachVersion('web3', (version, Web3) => {
})
const provider = version.includes('0.20')
? new Web3.providers.HttpProvider(`http://localhost:${port}`)
- : `ws://localhost${port}`
+ : `http://localhost${port}`
web3 = new Web3(provider)
config = { dappId: '123', web3, networkId: 1 }
assistInstance = da.init(config)
diff --git a/src/__tests__/js/web3.test.js b/src/__tests__/js/web3.test.js
index 386839d6..43fa8bfe 100644
--- a/src/__tests__/js/web3.test.js
+++ b/src/__tests__/js/web3.test.js
@@ -1,5 +1,4 @@
import truffleContract from 'truffle-contract'
-import da from '~/js'
import abi from '~/__tests__/res/dstoken.json'
import { initialState, updateState } from '~/js/helpers/state'
import * as websockets from '~/js/helpers/websockets'
@@ -18,8 +17,8 @@ const Web3v0p20 = multidepRequire('web3', '0.20.6')
const zeroAddress = '0x0000000000000000000000000000000000000000'
const initWeb3 = (simpleVersion, Web3) => {
- if (simpleVersion === '1.0') {
- return new Web3(`ws://localhost:${port}`)
+ if (simpleVersion === '1.') {
+ return new Web3(`http://localhost:${port}`)
}
const provider = new Web3.providers.HttpProvider(`http://localhost:${port}`)
return new Web3(provider)
@@ -30,7 +29,6 @@ describe(`web3.js tests`, () => {
describe(`using web3 ${version}`, () => {
describe('assist is initialised correctly', () => {
let web3
- let config
let simpleVersion
beforeEach(() => {
jest
@@ -39,22 +37,20 @@ describe(`web3.js tests`, () => {
jest
.spyOn(websockets, 'checkForSocketConnection')
.mockImplementation(() => Promise.resolve(true))
- simpleVersion = version.slice(0, 3)
+ simpleVersion = version.slice(0, 2)
web3 = initWeb3(simpleVersion, Web3)
- config = { dappId: '123', web3, networkId: 5 }
- da.init(config)
- })
- afterEach(() => {
- // need to close any websocket connection
- if (simpleVersion === '1.0') {
- web3.currentProvider.connection.close()
- }
+
+ updateState({
+ web3Instance: web3,
+ legacyWeb3: simpleVersion === '0.'
+ })
})
+
describe('web3Functions', () => {
describe('networkId', () => {
test('should return the expected networkId', async () => {
const networkId = await web3Functions.networkId(simpleVersion)()
- if (simpleVersion === '1.0') expect(networkId).toEqual(5)
+ if (simpleVersion === '1.') expect(networkId).toEqual(5)
else expect(networkId).toEqual('5') // 0.20 returns networkId as a string
})
})
@@ -145,7 +141,7 @@ describe(`web3.js tests`, () => {
describe('accounts', () => {
test(`should return the correct list of accounts`, async () => {
const expected =
- simpleVersion === '1.0'
+ simpleVersion === '1.'
? accounts
: accounts.map(a => a.toLowerCase())
const res = await web3Functions.accounts(simpleVersion)()
@@ -155,7 +151,7 @@ describe(`web3.js tests`, () => {
describe('txReceipt', () => {
test(`should return the correct receipt`, async () => {
const hash = await new Promise(resolve => {
- if (simpleVersion === '1.0') {
+ if (simpleVersion === '1.') {
web3.eth
.sendTransaction({
from: accounts[0],
diff --git a/src/js/helpers/events.js b/src/js/helpers/events.js
index ec030c34..8e88735b 100644
--- a/src/js/helpers/events.js
+++ b/src/js/helpers/events.js
@@ -23,6 +23,13 @@ export function handleEvent(eventObj, modalClickHandlers) {
let eventToLog = { ...event }
+ // remove receipt from what is sent to the server as it causes errors
+ if (eventToLog.transaction && eventToLog.transaction.receipt) {
+ const { transaction, ...rest } = eventToLog
+ const { receipt, ...txDetails } = transaction
+ eventToLog = { ...rest, transaction: txDetails }
+ }
+
// If dealing with a custom notification the logged event
// should have it's event and category code changed
if (categoryCode === 'userInitiatedNotify') {
diff --git a/src/js/helpers/state.js b/src/js/helpers/state.js
index 8f67a876..f278d5cb 100644
--- a/src/js/helpers/state.js
+++ b/src/js/helpers/state.js
@@ -37,7 +37,8 @@ export const initialState = {
iframeDocument: null,
iframeWindow: null,
connectionId: null,
- onboardPromise: null
+ onboardPromise: null,
+ nodeSynced: true
}
export let state = { ...initialState }
diff --git a/src/js/helpers/utilities.js b/src/js/helpers/utilities.js
index f073d427..ad319ee1 100644
--- a/src/js/helpers/utilities.js
+++ b/src/js/helpers/utilities.js
@@ -132,8 +132,24 @@ export function assistLog(log) {
}
export function extractMessageFromError(message) {
- const str = message.split('"message":')[1]
- return str.split('"')[1]
+ if (message.includes('User denied transaction signature')) {
+ return {
+ eventCode: 'txSendFail',
+ errorMsg: 'User denied transaction signature'
+ }
+ }
+
+ if (message.includes('transaction underpriced')) {
+ return {
+ eventCode: 'txUnderpriced',
+ errorMsg: 'Transaction is under priced'
+ }
+ }
+
+ return {
+ eventCode: 'txError',
+ errorMsg: message
+ }
}
export function eventCodeToType(eventCode) {
@@ -141,7 +157,8 @@ export function eventCodeToType(eventCode) {
case 'txRequest':
case 'txPending':
case 'txSent':
- case 'txStall':
+ case 'txStallPending':
+ case 'txStallConfirmed':
case 'txSpeedUp':
case 'txCancel':
case 'pending':
@@ -152,6 +169,7 @@ export function eventCodeToType(eventCode) {
case 'txRepeat':
case 'txAwaitingApproval':
case 'txConfirmReminder':
+ case 'txUnderpriced':
case 'error':
return 'failed'
case 'txConfirmed':
@@ -219,7 +237,8 @@ export const timeouts = {
checkSocketConnection: 250,
waitForResponse: 100,
txConfirmReminder: 20000,
- txStall: 30000,
+ txStallPending: 20000,
+ txStallConfirmed: 60000,
changeUI: 305,
localhostNetworkCheck: 300,
removeElement: 300,
diff --git a/src/js/helpers/validation.js b/src/js/helpers/validation.js
index 9160955c..6678c58b 100644
--- a/src/js/helpers/validation.js
+++ b/src/js/helpers/validation.js
@@ -1,5 +1,6 @@
/* eslint-disable import/prefer-default-export */
import ow from 'ow'
+import { assistLog } from './utilities'
const desktopPosition = ow.optional.string.is(
s =>
@@ -12,72 +13,84 @@ const desktopPosition = ow.optional.string.is(
const mobilePosition = ow.optional.string.is(s => s === 'bottom' || s === 'top')
export function validateConfig(config) {
- ow(
- config,
- 'config',
- ow.object.exactShape({
- networkId: ow.number,
- dappId: ow.string,
- web3: ow.optional.object,
- ethers: ow.optional.object,
- mobileBlocked: ow.optional.boolean,
- minimumBalance: ow.optional.string,
- headlessMode: ow.optional.boolean,
- messages: ow.optional.object.exactShape({
- txRequest: ow.optional.function,
- txSent: ow.optional.function,
- txPending: ow.optional.function,
- txSendFail: ow.optional.function,
- txStall: ow.optional.function,
- txFailed: ow.optional.function,
- nsfFail: ow.optional.function,
- txRepeat: ow.optional.function,
- txAwaitingApproval: ow.optional.function,
- txConfirmReminder: ow.optional.function,
- txConfirmed: ow.optional.function,
- txSpeedUp: ow.optional.function
- }),
- handleNotificationEvent: ow.optional.function,
- images: ow.optional.object.exactShape({
- welcome: ow.optional.object.exactShape({
- src: ow.string,
- srcset: ow.string
+ try {
+ ow(
+ config,
+ 'config',
+ ow.object.exactShape({
+ networkId: ow.number,
+ dappId: ow.string,
+ web3: ow.optional.object,
+ ethers: ow.optional.object,
+ mobileBlocked: ow.optional.boolean,
+ minimumBalance: ow.optional.string,
+ headlessMode: ow.optional.boolean,
+ messages: ow.optional.object.exactShape({
+ txRequest: ow.optional.function,
+ txSent: ow.optional.function,
+ txPending: ow.optional.function,
+ txSendFail: ow.optional.function,
+ txStallPending: ow.optional.function,
+ txStallConfirmed: ow.optional.function,
+ txFailed: ow.optional.function,
+ nsfFail: ow.optional.function,
+ txRepeat: ow.optional.function,
+ txAwaitingApproval: ow.optional.function,
+ txConfirmReminder: ow.optional.function,
+ txConfirmed: ow.optional.function,
+ txSpeedUp: ow.optional.function
}),
- complete: ow.optional.object.exactShape({
- src: ow.string,
- srcset: ow.string
- })
- }),
- style: ow.optional.object.exactShape({
- darkMode: ow.optional.boolean,
- notificationsPosition: ow.any(
- desktopPosition,
- ow.optional.object.exactShape({
- mobile: mobilePosition,
- desktop: desktopPosition
- })
- ),
- css: ow.optional.string
- }),
- timeouts: ow.optional.object.exactShape({
- txStall: ow.number
- }),
- recommendedWallets: ow.optional.object.exactShape({
- desktop: ow.optional.array.ofType(
- ow.object.exactShape({
- name: ow.string,
- link: ow.string,
- icon: ow.string
+ handleNotificationEvent: ow.optional.function,
+ images: ow.optional.object.exactShape({
+ welcome: ow.optional.object.exactShape({
+ src: ow.string,
+ srcset: ow.string
+ }),
+ complete: ow.optional.object.exactShape({
+ src: ow.string,
+ srcset: ow.string
})
- ).nonEmpty,
- mobile: ow.optional.array.ofType(
- ow.object.exactShape({
- name: ow.string,
- link: ow.string,
- icon: ow.string
- })
- ).nonEmpty
+ }),
+ style: ow.optional.object.exactShape({
+ darkMode: ow.optional.boolean,
+ notificationsPosition: ow.any(
+ desktopPosition,
+ ow.optional.object.exactShape({
+ mobile: mobilePosition,
+ desktop: desktopPosition
+ })
+ ),
+ css: ow.optional.string
+ }),
+ timeouts: ow.optional.object.exactShape({
+ txStallPending: ow.optional.number,
+ txStallConfirmed: ow.optional.number
+ }),
+ recommendedWallets: ow.optional.object.exactShape({
+ desktop: ow.optional.array.ofType(
+ ow.object.exactShape({
+ name: ow.string,
+ link: ow.string,
+ icon: ow.string
+ })
+ ).nonEmpty,
+ mobile: ow.optional.array.ofType(
+ ow.object.exactShape({
+ name: ow.string,
+ link: ow.string,
+ icon: ow.string
+ })
+ ).nonEmpty
+ })
})
- })
- )
+ )
+ } catch (error) {
+ if (error.message.includes('Did not expect property `txStall` to exist')) {
+ assistLog(
+ 'txStall events have now been separated in to txStallPending and txStallConfirmed events. Use the new eventCodes for custom messages on those events '
+ )
+ } else {
+ throw error
+ }
+ }
}
diff --git a/src/js/helpers/web3.js b/src/js/helpers/web3.js
index ff0b585b..25dd3fc4 100644
--- a/src/js/helpers/web3.js
+++ b/src/js/helpers/web3.js
@@ -9,9 +9,9 @@ errorObj.eventCode = 'initFail'
export const web3Functions = {
networkId: version => {
switch (version) {
- case '0.2':
+ case '0.':
return promisify(state.web3Instance.version.getNetwork)
- case '1.0':
+ case '1.':
return state.web3Instance.eth.net.getId
case 'ethers':
return () =>
@@ -27,10 +27,10 @@ export const web3Functions = {
},
bigNumber: version => {
switch (version) {
- case '0.2':
+ case '0.':
return value =>
Promise.resolve(state.web3Instance.toBigNumber(formatNumber(value)))
- case '1.0':
+ case '1.':
return value =>
Promise.resolve(state.web3Instance.utils.toBN(formatNumber(value)))
case 'ethers':
@@ -48,9 +48,9 @@ export const web3Functions = {
},
gasPrice: version => {
switch (version) {
- case '0.2':
+ case '0.':
return promisify(state.web3Instance.eth.getGasPrice)
- case '1.0':
+ case '1.':
return state.web3Instance.eth.getGasPrice
case 'ethers':
return () =>
@@ -66,7 +66,7 @@ export const web3Functions = {
},
contractGas: (version, truffleContract) => {
switch (version) {
- case '0.2':
+ case '0.':
return ({ contractObj, methodName, overloadKey, args }) => {
const contractMethod = getContractMethod({
contractObj,
@@ -80,7 +80,7 @@ export const web3Functions = {
: promisify(contractMethod.estimateGas)(...args)
}
- case '1.0':
+ case '1.':
return ({ contractObj, methodName, overloadKey, args, txOptions }) => {
const contractMethod = getContractMethod({
contractObj,
@@ -102,9 +102,9 @@ export const web3Functions = {
},
transactionGas: version => {
switch (version) {
- case '0.2':
+ case '0.':
return promisify(state.web3Instance.eth.estimateGas)
- case '1.0':
+ case '1.':
return state.web3Instance.eth.estimateGas
case 'ethers':
return txOptions =>
@@ -120,9 +120,9 @@ export const web3Functions = {
},
balance: version => {
switch (version) {
- case '0.2':
+ case '0.':
return promisify(state.web3Instance.eth.getBalance)
- case '1.0':
+ case '1.':
return state.web3Instance.eth.getBalance
case 'ethers':
return address =>
@@ -139,9 +139,9 @@ export const web3Functions = {
},
accounts: version => {
switch (version) {
- case '0.2':
+ case '0.':
return promisify(state.web3Instance.eth.getAccounts)
- case '1.0':
+ case '1.':
return state.web3Instance.eth.getAccounts
case 'ethers':
return () =>
@@ -162,6 +162,7 @@ export const web3Functions = {
export function configureWeb3(web3) {
if (!web3) {
web3 = window.web3 // eslint-disable-line prefer-destructuring
+ if (!web3) return
}
// If web3 has been prefaced with the default property, re-assign it
@@ -201,37 +202,72 @@ export function configureWeb3(web3) {
})
}
-export function checkForWallet() {
- if (window.ethereum) {
- updateState({
- currentProvider: getCurrentProvider(),
- validBrowser: true,
- web3Wallet: true,
- legacyWallet: false,
- modernWallet: true
- })
- } else if (window.web3 && window.web3.version) {
- updateState({
- currentProvider: getCurrentProvider(),
- validBrowser: true,
- web3Wallet: true,
- legacyWallet: true,
- modernWallet: false
- })
+export async function checkForWallet() {
+ if (
+ state.web3Instance &&
+ state.web3Instance.currentProvider &&
+ typeof state.web3Instance.currentProvider.send === 'function'
+ ) {
+ if (typeof state.web3Instance.currentProvider.enable === 'function') {
+ updateState({
+ currentProvider: getCurrentProvider(),
+ validBrowser: true,
+ web3Wallet: true,
+ legacyWallet: false,
+ modernWallet: true
+ })
+ } else {
+ const accounts = await getAccounts().catch(handleWeb3Error)
+
+ if (accounts && accounts[0]) {
+ updateState({
+ currentProvider: getCurrentProvider(),
+ validBrowser: true,
+ web3Wallet: true,
+ legacyWallet: true,
+ modernWallet: false
+ })
+ } else {
+ updateState({
+ web3Wallet: false,
+ accessToAccounts: false,
+ walletLoggedIn: false,
+ walletEnabled: false
+ })
+ }
+ }
} else {
- updateState({
- web3Wallet: false,
- accessToAccounts: false,
- walletLoggedIn: false,
- walletEnabled: false
- })
+ if (window.ethereum) {
+ updateState({
+ currentProvider: getCurrentProvider(),
+ validBrowser: true,
+ web3Wallet: true,
+ legacyWallet: false,
+ modernWallet: true
+ })
+ } else if (window.web3 && window.web3.version) {
+ updateState({
+ currentProvider: getCurrentProvider(),
+ validBrowser: true,
+ web3Wallet: true,
+ legacyWallet: true,
+ modernWallet: false
+ })
+ } else {
+ updateState({
+ web3Wallet: false,
+ accessToAccounts: false,
+ walletLoggedIn: false,
+ walletEnabled: false
+ })
+ }
}
}
export function getNetworkId() {
const version = state.config.ethers
? 'ethers'
- : state.web3Version && state.web3Version.slice(0, 3)
+ : state.web3Version && state.web3Version.slice(0, 2)
return web3Functions
.networkId(version)()
.then(id => Number(id))
@@ -247,7 +283,7 @@ export function getTransactionParams({
return new Promise(async resolve => {
const version = state.config.ethers
? 'ethers'
- : state.web3Version && state.web3Version.slice(0, 3)
+ : state.web3Version && state.web3Version.slice(0, 2)
// Sometimes value is in exponent notation and needs to be formatted
if (txOptions.value) {
@@ -314,7 +350,7 @@ export async function hasSufficientBalance({
return new Promise(async resolve => {
const version = state.config.ethers
? 'ethers'
- : state.web3Version && state.web3Version.slice(0, 3)
+ : state.web3Version && state.web3Version.slice(0, 2)
const gasCost = gas.mul(gasPrice)
@@ -342,11 +378,13 @@ export function getAccountBalance() {
return new Promise(async resolve => {
const accounts = await getAccounts().catch(handleWeb3Error)
+ if (!accounts || !accounts[0]) return
+
updateState({ accountAddress: accounts && accounts[0] })
const version = state.config.ethers
? 'ethers'
- : state.web3Version && state.web3Version.slice(0, 3)
+ : state.web3Version && state.web3Version.slice(0, 2)
const balance = await web3Functions
.balance(version)(accounts[0])
.catch(handleWeb3Error)
@@ -377,7 +415,7 @@ export function getContractMethod({
export function getAccounts() {
const version = state.config.ethers
? 'ethers'
- : state.web3Version && state.web3Version.slice(0, 3)
+ : state.web3Version && state.web3Version.slice(0, 2)
return web3Functions.accounts(version)()
}
@@ -396,11 +434,11 @@ export function getCurrentProvider() {
const web3 = state.web3Instance
if (!web3) {
- if (window.ethereum.isMetaMask) {
+ if (window.ethereum && window.ethereum.isMetaMask) {
return 'metamask'
}
- if (window.ethereum.isDapper) {
+ if (window.ethereum && window.ethereum.isDapper) {
return 'dapper'
}
@@ -452,6 +490,10 @@ export function getCurrentProvider() {
if (web3.currentProvider.connection) {
return 'Infura Websocket'
}
+
+ if (web3.currentProvider.name === 'trezor') {
+ return 'trezor'
+ }
}
// Poll for a tx receipt
diff --git a/src/js/helpers/websockets.js b/src/js/helpers/websockets.js
index a3760418..5d10b50b 100644
--- a/src/js/helpers/websockets.js
+++ b/src/js/helpers/websockets.js
@@ -1,7 +1,7 @@
import { state, updateState } from './state'
import { handleEvent } from './events'
import { storeItem, getItem } from './storage'
-import { timeouts } from './utilities'
+import { timeouts, networkName } from './utilities'
import {
updateTransactionInQueue,
getTxObjFromQueue,
@@ -66,12 +66,22 @@ export function retryLogEvent(logFunc) {
// Handle in coming socket messages
export function handleSocketMessage(msg) {
- const { status, reason, event, connectionId } = JSON.parse(msg.data)
+ const { status, reason, event, connectionId, nodeSyncStatus } = JSON.parse(
+ msg.data
+ )
const { validApiKey, supportedNetwork } = state
if (!validApiKey || !supportedNetwork) {
return
}
+ if (
+ nodeSyncStatus !== undefined &&
+ nodeSyncStatus.blockchain === 'ethereum' &&
+ nodeSyncStatus.network === networkName(state.config.networkId)
+ ) {
+ updateState({ nodeSynced: nodeSyncStatus.synced })
+ }
+
// handle any errors from the server
if (status === 'error') {
if (
diff --git a/src/js/index.js b/src/js/index.js
index 240358bf..ac302fe2 100644
--- a/src/js/index.js
+++ b/src/js/index.js
@@ -452,6 +452,25 @@ function init(config) {
// it only needs to be assigned once
if (!seenMethods.includes(name)) {
const method = contractObj.methods[name]
+
+ /* If the developer has minified constructor names, a truffle contract may
+ * have incorrectly been identified as a web3 contract and flow would incorrectly
+ * get here. In this case, 'method' would be undefined.
+ * Do a quick check to make sure it exists.
+ */
+ if (!method)
+ throw Error(
+ 'It looks like some function names that assist.js relies on have been minified in this build, causing it to incorrectly identify a Truffle contract as a web3.js contract.' +
+ "\nIf you wish to use Truffle contracts with assist.js, you need to disable minification of 'fnames' in your build." +
+ '\nInstructions for:' +
+ '\n - Terser: https://github.com/terser-js/terser#minify-options' +
+ '\n - Uglify: https://github.com/mishoo/UglifyJS2#minify-options' +
+ '\n - Webpack terser plugin: https://github.com/webpack-contrib/terser-webpack-plugin#terseroptions' +
+ '\n - Webpack uglify plugin: https://github.com/webpack-contrib/uglifyjs-webpack-plugin#uglifyoptions' +
+ '\n - Rollup terser plugin: https://github.com/TrySound/rollup-plugin-terser#options' +
+ '\n - Rollup uglify plugin: https://github.com/TrySound/rollup-plugin-uglify#options'
+ )
+
methodsObj[name] = (...args) =>
constant
? call({ contractObj, methodName: name, args, truffleContract })
diff --git a/src/js/logic/send-transaction.js b/src/js/logic/send-transaction.js
index 60cfc12e..8b88fac2 100644
--- a/src/js/logic/send-transaction.js
+++ b/src/js/logic/send-transaction.js
@@ -291,8 +291,8 @@ export function onTxHash(id, hash, categoryCode) {
}
})
- const customStallTimeout =
- state.config.timeouts && state.config.timeouts.txStall
+ const customStallPendingTimeout =
+ state.config.timeouts && state.config.timeouts.txStallPending
// Check if transaction is in txPool after timeout
setTimeout(() => {
@@ -303,14 +303,11 @@ export function onTxHash(id, hash, categoryCode) {
transaction: { status }
} = txObj
- if (
- state.socketConnection &&
- (status === 'approved' || status === 'pending')
- ) {
- updateTransactionInQueue(id, { status: 'stalled' })
+ if (state.socketConnection && status === 'approved' && state.nodeSynced) {
+ updateTransactionInQueue(id, { status: 'stalledPending' })
handleEvent({
- eventCode: 'txStall',
+ eventCode: 'txStallPending',
categoryCode,
transaction: txObj.transaction,
contract: txObj.contract,
@@ -324,7 +321,39 @@ export function onTxHash(id, hash, categoryCode) {
}
})
}
- }, customStallTimeout || timeouts.txStall)
+ }, customStallPendingTimeout || timeouts.txStallPending)
+
+ const customStallConfirmedTimeout =
+ state.config.timeouts && state.config.timeouts.txStallConfirmed
+
+ // Check if transaction is still in txPool after timeout
+ setTimeout(() => {
+ const txObj = getTxObjFromQueue(id)
+ if (!txObj) return
+
+ const {
+ transaction: { status, originalHash }
+ } = txObj
+
+ // check originalHash to make sure not speedup or cancel
+ if (state.socketConnection && status === 'pending' && !originalHash) {
+ updateTransactionInQueue(id, { status: 'stalledConfirmed' })
+
+ handleEvent({
+ eventCode: 'txStallConfirmed',
+ categoryCode,
+ transaction: txObj.transaction,
+ contract: txObj.contract,
+ inlineCustomMsgs: txObj.inlineCustomMsgs,
+ wallet: {
+ provider: state.currentProvider,
+ address: state.accountAddress,
+ balance: state.accountBalance,
+ minimum: state.config.minimumBalance
+ }
+ })
+ }
+ }, customStallConfirmedTimeout || timeouts.txStallConfirmed)
}
async function onTxReceipt(id, categoryCode, receipt) {
@@ -357,32 +386,33 @@ async function onTxReceipt(id, categoryCode, receipt) {
}
function onTxError(id, error, categoryCode) {
- const { message } = error
- let errorMsg
- try {
- errorMsg = extractMessageFromError(message)
- } catch (error) {
- errorMsg = 'User denied transaction signature'
- }
+ const { errorMsg, eventCode } = extractMessageFromError(error.message)
- const txObj = updateTransactionInQueue(id, { status: 'rejected' })
+ let txObj = getTxObjFromQueue(id)
- handleEvent({
- eventCode:
- errorMsg === 'transaction underpriced' ? 'txUnderpriced' : 'txSendFail',
- categoryCode,
- transaction: txObj.transaction,
- contract: txObj.contract,
- inlineCustomMsgs: txObj.inlineCustomMsgs,
- clickHandlers: txObj.clickHandlers,
- reason: errorMsg,
- wallet: {
- provider: state.currentProvider,
- address: state.accountAddress,
- balance: state.accountBalance,
- minimum: state.config.minimumBalance
- }
- })
+ if (
+ txObj &&
+ (txObj.transaction.status !== 'confirmed' ||
+ txObj.transaction.status !== 'completed')
+ ) {
+ txObj = updateTransactionInQueue(id, { status: 'error' })
+
+ handleEvent({
+ eventCode,
+ categoryCode,
+ transaction: txObj.transaction,
+ contract: txObj.contract,
+ inlineCustomMsgs: txObj.inlineCustomMsgs,
+ clickHandlers: txObj.clickHandlers,
+ reason: errorMsg,
+ wallet: {
+ provider: state.currentProvider,
+ address: state.accountAddress,
+ balance: state.accountBalance,
+ minimum: state.config.minimumBalance
+ }
+ })
+ }
removeTransactionFromQueue(id)
}
diff --git a/src/js/logic/user.js b/src/js/logic/user.js
index 63f5cb39..94806d6a 100644
--- a/src/js/logic/user.js
+++ b/src/js/logic/user.js
@@ -21,7 +21,7 @@ export function checkUserEnvironment() {
checkValidBrowser()
}
- checkForWallet()
+ await checkForWallet()
if (!state.web3Wallet) {
if (!state.mobileDevice) {
@@ -271,7 +271,7 @@ function checkMinimumBalance() {
const { web3Version } = state
const version = state.config.ethers
? 'ethers'
- : web3Version && web3Version.slice(0, 3)
+ : web3Version && web3Version.slice(0, 2)
const minimum = state.config.minimumBalance || 0
const balance = await getAccountBalance().catch(resolve)
diff --git a/src/js/views/content.js b/src/js/views/content.js
index 72ad5a12..03f1ecc8 100644
--- a/src/js/views/content.js
+++ b/src/js/views/content.js
@@ -362,8 +362,10 @@ export const transactionMsgs = {
`Your transaction ID: ${transaction.nonce} has started`,
txSent: () => `Your transaction has been sent to the network`,
txSendFail: () => `You rejected the transaction`,
- txStall: ({ transaction }) =>
- `Your transaction ID: ${transaction.nonce} has stalled`,
+ txStallPending: () =>
+ 'Your transaction has stalled and has not entered the transaction pool',
+ txStallConfirmed: ({ transaction }) =>
+ `Your transaction ID: ${transaction.nonce} has stalled and hasn't been confirmed`,
txFailed: ({ transaction }) =>
`Your transaction ID: ${transaction.nonce} has failed`,
nsfFail: () => 'You have insufficient funds to complete this transaction',
@@ -377,5 +379,7 @@ export const transactionMsgs = {
txSpeedUp: ({ transaction }) =>
`Your transaction ID: ${transaction.nonce} has been sped up`,
txCancel: ({ transaction }) =>
- `Your transaction ID: ${transaction.nonce} is being canceled`
+ `Your transaction ID: ${transaction.nonce} is being canceled`,
+ txUnderpriced: () =>
+ 'The gas price for your transaction is too low, try again with a higher gas price'
}
diff --git a/src/js/views/event-to-ui.js b/src/js/views/event-to-ui.js
index a87652d7..0e46049f 100644
--- a/src/js/views/event-to-ui.js
+++ b/src/js/views/event-to-ui.js
@@ -74,10 +74,12 @@ const eventToUI = {
txConfirmReminder: notificationsUI,
txConfirmed: notificationsUI,
txConfirmedClient: notificationsUI,
- txStall: notificationsUI,
+ txStallPending: notificationsUI,
+ txStallConfirmed: notificationsUI,
txFailed: notificationsUI,
txSpeedUp: notificationsUI,
- txCancel: notificationsUI
+ txCancel: notificationsUI,
+ txUnderpriced: notificationsUI
},
activeContract: {
txAwaitingApproval: notificationsUI,
@@ -88,10 +90,12 @@ const eventToUI = {
txConfirmReminder: notificationsUI,
txConfirmed: notificationsUI,
txConfirmedClient: notificationsUI,
- txStall: notificationsUI,
+ txStallPending: notificationsUI,
+ txStallConfirmed: notificationsUI,
txFailed: notificationsUI,
txSpeedUp: notificationsUI,
- txCancel: notificationsUI
+ txCancel: notificationsUI,
+ txUnderpriced: notificationsUI
},
userInitiatedNotify: {
success: notificationsUI,
@@ -199,7 +203,8 @@ function notificationsUI({
const hasTimer =
eventCode === 'txPending' ||
eventCode === 'txSent' ||
- eventCode === 'txStall' ||
+ eventCode === 'txStallPending' ||
+ eventCode === 'txStallConfirmed' ||
eventCode === 'txSpeedUp' ||
eventCode === 'pending'