Skip to content

Testing with global web3 mocks

Terrance Li edited this page Oct 15, 2020 · 1 revision

To make it easier to write shorter tests, we are mocking web3 globally.

How does this work?

In utils/web3mock.js, we defined our "mock" version of web3. It has similar behavior to the real thing, only it does not actually return real-time live data from a blockchain. Instead, it processes and returns data seeded to it in your tests.

Whenever a test is run with Jest, it replaces all imports for web3 with @/utils/web3mock, which achieves the global mock.

How do I use this? How do I seed data?

The mock module has some static fields, which you can set to your seed data:

static MOCK_ACCOUNTS = {};
static MOCK_TRANSACTIONS = [];
static VALID_ADDRESSES = [];
static CONTRACT_ADDRESSES = [];
static TOTAL_SUPPLY = 0;

/**
 * Transaction: {
 *    transactionHash: String,
 *    data: String, // amount transfered in hex, times 10 ** 6
 *    sender: String, // hex for sender address
 *    receiver: String, // hex for receiver address
 *    blockNumber: Number
 * }
 * 
 * Account: {
 *    balance: Number,
 *    minter: Boolean,
 *    pauser: Boolean,
 *    owner: Boolean,
 *    blacklisted: Boolean
 * }
 * 
 * @param {Object<key: String, value: Account>} MOCK_ACCOUNTS Map of wallet addresses to accounts
 * @param {Transaction[]} MOCK_TRANSACTIONS Array of mock transactions (Transaction structure above)
 * @param {String[]} VALID_ADDRESSES Array of valid addresses (for utils.isAddress)
 * @param {String[]} CONTRACT_ADDRESSES Subset of VALID_ADDRESSES that are contract addresses (for getCode)
 * @param {Integer} TOTAL_SUPPLY Total supply 
 */

Inside your test, if you wanted to seed the module with certain accounts, you first import Web3 from 'web3 (as normal), and then set Web3.MOCK_ACCOUNTS = {...}. Look at tests/unit/Transactions.spec.js for a larger example. Here's a snippet from that file:

import Web3 from 'web3';
...
const MOCK_WALLET_ADDRESS = padHex('0x123456789abcdef', 64)
const MOCK_TRANSACTIONS = [
  {
    data: '0x010121',
    transactionHash: '0x0999',
    blockNumber: 2,
    sender: MOCK_WALLET_ADDRESS,
    receiver: padHex('0x232323', 64)
  },
  {
    data: '0x0109',
    transactionHash: '0x01111',
    blockNumber: 3,
    sender: MOCK_WALLET_ADDRESS,
    receiver: padHex('0x288765', 64)
  },
  ...
]

Web3.MOCK_TRANSACTIONS = MOCK_TRANSACTIONS

describe('_address.vue', () => {
  test('getLogs fetches correct logs 1', async () => {
    ...
  }
  ...
}

Clone this wiki locally