Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature: Add stuckTransfers #8

Merged
merged 1 commit into from
Aug 24, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 29 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,32 @@ Example of an API
}
```

* `GET /stuckTransfers` - check stucked transfers that wasnot called by transferAndCall
```json
{

"stuckTransfers": [
{
"address": "0x6758B7d441a9739b98552B373703d8d3d14f9e62",
"blockNumber": 5964312,
"transactionHash": "0x74413ba79509a292d5d0d6edd364b3617c83a57b13d603de9deb6c8e6b6c6daf",
...
"returnValues": {
"0": "0x8D4bbc1B533aB9e3a743210870b6e3c4c0f7E935",
"1": "0xd819E948b14cA6AAD2b7Ffd333cCDf732b129EeD",
"2": "10000000000000000000000",
"from": "0x8D4bbc1B533aB9e3a743210870b6e3c4c0f7E935",
"to": "0xd819E948b14cA6AAD2b7Ffd333cCDf732b129EeD",
"value": "10000000000000000000000"
},
...
}
],
"total": 2,
"lastChecked": 1535058662
}
```

# How to run
Create .env file (see `.env.example` for parameters reference)
```bash
Expand All @@ -110,6 +136,9 @@ npm i
node checkWorker.js
# check unprocessed events
node checkWorker2.js
# check stuck transfers called by transfer, not transferAndCall
# only applicable for bridge-rust-v1-native-to-erc
node checkWorker3.js
# run web interface
node index.js
```
Expand Down
19 changes: 19 additions & 0 deletions checkWorker3.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
const fs = require('fs')
const logger = require('./logger')('checkWorker3');
const stuckTransfers = require('./stuckTransfers')

async function checkWorker3() {
try {
logger.debug('calling stuckTransfers()');
const transfers = await stuckTransfers();
console.log(transfers)
if (!transfers) throw new Error('transfers is empty: ' + JSON.stringify(transfers));
fs.writeFileSync(__dirname + '/responses/stuckTransfers.json', JSON.stringify(transfers,null,4));
logger.debug("Done");
return transfers;
} catch(e) {
logger.error('checkWorker3.js', e);
throw e;
}
}
checkWorker3();
14 changes: 14 additions & 0 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,20 @@ app.get('/eventsStats', async (req, res, next) => {
}
})

// responses/stuckTransfers.json
app.get('/stuckTransfers', async (req, res, next) => {
try {
const results = await readFile('./responses/stuckTransfers.json');
results.ok = (
results.total.length == 0
);
res.json(results);
} catch (e) {
//this will eventually be handled by your error handling middleware
next(e)
}
})

const port = process.env.PORT || 3000;
app.set('port', port);
app.listen(port, () => console.log('Monitoring app listening on port 3000!'))
107 changes: 107 additions & 0 deletions stuckTransfers.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
require('dotenv').config();
const logger = require('./logger')('stuckTransfers.js');
const Web3 = require('web3');
const Web3Utils = require('web3-utils')
const FOREIGN_RPC_URL = process.env.FOREIGN_RPC_URL;
const FOREIGN_BRIDGE_ADDRESS = process.env.FOREIGN_BRIDGE_ADDRESS;
const POA20_ADDRESS = process.env.POA20_ADDRESS;
const FOREIGN_DEPLOYMENT_BLOCK = Number(process.env.FOREIGN_DEPLOYMENT_BLOCK) || 0;

const foreignProvider = new Web3.providers.HttpProvider(FOREIGN_RPC_URL);
const web3Foreign = new Web3(foreignProvider);

const ABI_TransferWithoutData = [
{
"anonymous": false,
"inputs": [
{
"indexed": true,
"name": "from",
"type": "address"
},
{
"indexed": true,
"name": "to",
"type": "address"
},
{
"indexed": false,
"name": "value",
"type": "uint256"
}
],
"name": "Transfer",
"type": "event"
}
]

const ABI_withData = [{
"anonymous": false,
"inputs": [
{
"indexed": true,
"name": "from",
"type": "address"
},
{
"indexed": true,
"name": "to",
"type": "address"
},
{
"indexed": false,
"name": "value",
"type": "uint256"
},
{
"indexed": false,
"name": "data",
"type": "bytes"
}
],
"name": "Transfer",
"type": "event"
}]

function compareTransfers(transfersNormal){
return function(withData){
return transfersNormal.filter(function(normal){
return normal.transactionHash === withData.transactionHash
}).length == 0;
}
}

async function main(){
try {
const tokenContract = new web3Foreign.eth.Contract(ABI_TransferWithoutData, POA20_ADDRESS);
const tokenContractWithData = new web3Foreign.eth.Contract(ABI_withData, POA20_ADDRESS);
logger.debug('calling tokenContract.getPastEvents Transfer');
let transfersNormal = await tokenContract.getPastEvents('Transfer', {
filter: {
to: FOREIGN_BRIDGE_ADDRESS
},
fromBlock: FOREIGN_DEPLOYMENT_BLOCK,
toBlock: 'latest'
});
logger.debug('calling tokenContractWithData.getPastEvents Transfer');
let transfersWithData = await tokenContractWithData.getPastEvents('Transfer', {
filter: {
to: FOREIGN_BRIDGE_ADDRESS
},
fromBlock: FOREIGN_DEPLOYMENT_BLOCK,
toBlock: 'latest'
});
const stuckTransfers = transfersNormal.filter(compareTransfers(transfersWithData))
logger.debug('Done');
return {
stuckTransfers,
total: stuckTransfers.length,
lastChecked: Math.floor(Date.now() / 1000)
}
} catch(e) {
logger.error(e);
throw e;
}

}
module.exports = main;