diff --git a/lib/tests/test.js b/lib/tests/test.js index f83f276e..9345f8f7 100644 --- a/lib/tests/test.js +++ b/lib/tests/test.js @@ -99,7 +99,42 @@ class Test { if (!this.sim) { this.sim = getSimulator(); } - this.web3.setProvider(this.sim.provider(this.simOptions)); + + let simProvider = this.sim.provider(this.simOptions); + + // Here we patch the sendAsync method on the provider. The goal behind this is to force pure/constant/view calls to become + // transactions, so that we can pull in execution traces and account for those executions in code coverage. + // + // Instead of a simple call, here's what happens: + // + // 1) A transaction is sent with the same payload, and a pre-defined gas price; + // 2) We wait for the transaction to be mined by asking for the receipt; + // 3) Once we get the receipt back, we dispatch the real call and pass the original callback; + // + // This will still allow tests to get the return value from the call and run contracts unmodified. + simProvider.realSendAsync = simProvider.sendAsync.bind(simProvider); + simProvider.sendAsync = function(payload, cb) { + if(payload.method !== 'eth_call') { + return simProvider.realSendAsync(payload, cb); + } + + let newParams = Object.assign({}, payload.params[0], {gasPrice: '0x77359400'}); + let newPayload = { + id: payload.id + 1, + method: 'eth_sendTransaction', + params: [newParams], + jsonrpc: payload.jsonrpc + }; + + simProvider.realSendAsync(newPayload, (_err, response) => { + let txHash = response.result; + self.web3.eth.getTransactionReceipt(txHash, (_err, _res) => { + simProvider.realSendAsync(payload, cb); + }); + }); + }; + + this.web3.setProvider(simProvider); callback(); }