From da45dbff8ba982cd08c2b5057083df5a0a949cf7 Mon Sep 17 00:00:00 2001 From: talha Date: Thu, 6 Jan 2022 09:01:56 +0500 Subject: [PATCH 1/5] erc20 and erc721 logging issues --- index.js | 58 ++++++++++++++++++++++++++++++++-------------------- package.json | 2 ++ 2 files changed, 38 insertions(+), 22 deletions(-) diff --git a/index.js b/index.js index 1c5e5d1..cc73dda 100644 --- a/index.js +++ b/index.js @@ -1,9 +1,11 @@ const { sha3, BN } = require("web3-utils"); const abiCoder = require("web3-eth-abi"); - +// topic id erc20 and erc721 +const transferSignature = "ddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef"; const state = { savedABIs: [], methodIDs: {}, + erc20IDs:{} }; function _getABIs() { @@ -32,7 +34,11 @@ function _addABI(abiArray) { ")" ); if (abi.type === "event") { - state.methodIDs[signature.slice(2)] = abi; + // add erc20 event in separate array + if ( state.methodIDs[signature.slice(2)] && signature.slice(2) === transferSignature) + state.erc20IDs[[signature.slice(2)]] = abi; + else + state.methodIDs[signature.slice(2)] = abi; } else { state.methodIDs[signature.slice(2, 10)] = abi; } @@ -131,12 +137,21 @@ function _decodeMethod(data) { } function _decodeLogs(logs) { - return logs.filter(log => log.topics.length > 0).map((logItem) => { - const methodID = logItem.topics[0].slice(2); - const method = state.methodIDs[methodID]; + const logsToProcess = logs.filter(log => log.topics.length > 0); + const resultSet = []; + for (let index = 0; index < logsToProcess.length; index++) { + let method; + const log = logsToProcess[index]; + const methodID = log.topics[0].slice(2); + // methodid mathches with erc20 transfer event and topic count length is 3 + // it means its erc20 transaction + if (methodID === transferSignature && log.topics.length===3) + method = state.erc20IDs[methodID]; + else + method = state.methodIDs[methodID]; + let decodedParams = []; if (method) { - const logData = logItem.data; - let decodedParams = []; + const logData = log.data; let dataIndex = 0; let topicsIndex = 1; @@ -146,27 +161,26 @@ function _decodeLogs(logs) { dataTypes.push(input.type); } }); - const decodedData = abiCoder.decodeParameters( dataTypes, logData.slice(2) ); - + // Loop topic and data to get the params method.inputs.map(function(param) { let decodedP = { name: param.name, type: param.type, }; - + if (param.indexed) { - decodedP.value = logItem.topics[topicsIndex]; + decodedP.value = log.topics[topicsIndex]; topicsIndex++; } else { decodedP.value = decodedData[dataIndex]; dataIndex++; } - + if (param.type === "address") { decodedP.value = decodedP.value.toLowerCase(); // 42 because len(0x) + 40 @@ -177,11 +191,11 @@ function _decodeLogs(logs) { decodedP.value = temp.join(""); } } - + if ( param.type === "uint256" || - param.type === "uint8" || - param.type === "int" + param.type === "uint8" || + param.type === "int" ) { // ensure to remove leading 0x for hex numbers if (typeof decodedP.value === "string" && decodedP.value.startsWith("0x")) { @@ -189,19 +203,19 @@ function _decodeLogs(logs) { } else { decodedP.value = new BN(decodedP.value).toString(10); } - + } - + decodedParams.push(decodedP); }); - - return { + resultSet.push({ name: method.name, events: decodedParams, - address: logItem.address, - }; + address: log.address, + }); } - }); + } + return resultSet; } module.exports = { diff --git a/package.json b/package.json index 48f5cd0..29b4d86 100644 --- a/package.json +++ b/package.json @@ -5,6 +5,8 @@ "main": "index.js", "scripts": { "pretest": "eslint --ignore-path .eslintignore .", + "lint": "./node_modules/.bin/eslint ./", + "lint:fix": "eslint ./ --fix", "test": "mocha test", "dist": "webpack" }, From a743b70c19af08b543b1e6f4c85938bd9b211043 Mon Sep 17 00:00:00 2001 From: talha Date: Thu, 6 Jan 2022 15:07:13 +0500 Subject: [PATCH 2/5] edition of test case --- index.js | 4 ++++ test/test.js | 32 ++++++++++++++++++++++++++++++++ 2 files changed, 36 insertions(+) diff --git a/index.js b/index.js index cc73dda..2751a64 100644 --- a/index.js +++ b/index.js @@ -147,6 +147,10 @@ function _decodeLogs(logs) { // it means its erc20 transaction if (methodID === transferSignature && log.topics.length===3) method = state.erc20IDs[methodID]; + // if the dev have not supplied the erc721 abi, we will fetch erc20 method event info from methods + if (!method){ + method = state.methodIDs[methodID]; + } else method = state.methodIDs[methodID]; let decodedParams = []; diff --git a/test/test.js b/test/test.js index 03104f0..949d315 100644 --- a/test/test.js +++ b/test/test.js @@ -170,4 +170,36 @@ describe("abi decoder", function () { expect(Object.keys(methods)).to.have.length(39); }); + it("decode erc20 logs", () => { + const testABI = [{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"value","type":"uint256"}],"name":"Transfer","type":"event"}]; + abiDecoder.addABI(testABI); + const testLogs = [ + { + data: "0x00000000000000000000000000000000000000000000000c1b1c7851eb4743ed", + topics: [ + "0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef", + "0x0000000000000000000000009963c5d9b0a02d6316e546677c73932b0a60df1f", + "0x000000000000000000000000fd79fa24d5a883e90ed60d1c080f49cba6c925da", + ], + address: "0x2E10348eE563dEc5FE483DE558D1946b7A3372c2" + } + ]; + const decodedLogs = abiDecoder.decodeLogs(testLogs); + expect(decodedLogs).to.be.an("array"); + expect(decodedLogs).to.have.length(1); + expect(decodedLogs[0].name).to.equal("Transfer"); + expect(decodedLogs[0].events).to.have.length(3); + expect(decodedLogs[0].address).to.equal("0x2E10348eE563dEc5FE483DE558D1946b7A3372c2"); + expect(decodedLogs[0].events[0].name).to.equal("from"); + expect(decodedLogs[0].events[0].type).to.equal("address"); + expect(decodedLogs[0].events[0].value).to.equal("0x9963c5d9b0a02d6316e546677c73932b0a60df1f"); + expect(decodedLogs[0].events[1].name).to.equal("to"); + expect(decodedLogs[0].events[1].type).to.equal("address"); + expect(decodedLogs[0].events[1].value).to.equal("0xfd79fa24d5a883e90ed60d1c080f49cba6c925da"); + expect(decodedLogs[0].events[2].type).to.equal("uint256"); + expect(decodedLogs[0].events[2].name).to.equal("value"); + expect(decodedLogs[0].events[2].value).to.equal("223314497516121572333"); + + }); + }); From 1d3f9c411deed8e6c65a36610615e813e82d016e Mon Sep 17 00:00:00 2001 From: talha Date: Wed, 12 Jan 2022 12:48:02 +0500 Subject: [PATCH 3/5] fix missing erc721 abi thing --- index.js | 6 ++++-- test/test.js | 36 ++++++++++++++++++++++++++++++++++++ 2 files changed, 40 insertions(+), 2 deletions(-) diff --git a/index.js b/index.js index 2751a64..5ac3655 100644 --- a/index.js +++ b/index.js @@ -145,12 +145,14 @@ function _decodeLogs(logs) { const methodID = log.topics[0].slice(2); // methodid mathches with erc20 transfer event and topic count length is 3 // it means its erc20 transaction - if (methodID === transferSignature && log.topics.length===3) + if (methodID === transferSignature && log.topics.length===3){ method = state.erc20IDs[methodID]; // if the dev have not supplied the erc721 abi, we will fetch erc20 method event info from methods - if (!method){ + if (!method){ method = state.methodIDs[methodID]; } + } + else method = state.methodIDs[methodID]; let decodedParams = []; diff --git a/test/test.js b/test/test.js index 949d315..897ddcd 100644 --- a/test/test.js +++ b/test/test.js @@ -201,5 +201,41 @@ describe("abi decoder", function () { expect(decodedLogs[0].events[2].value).to.equal("223314497516121572333"); }); + it("decode erc721 logs", () => { + const testABI = [{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{ + "indexed": true, + "internalType": "uint256", + "name": "tokenId", + "type": "uint256" + }],"name":"Transfer","type":"event"}]; + abiDecoder.addABI(testABI); + const testLogs = [ + { + data: "0x00000000000000000000000000000000000000000000000c1b1c7851eb4743ed", + topics: [ + "0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef", + "0x0000000000000000000000009963c5d9b0a02d6316e546677c73932b0a60df1f", + "0x000000000000000000000000fd79fa24d5a883e90ed60d1c080f49cba6c925da", + ], + address: "0x2E10348eE563dEc5FE483DE558D1946b7A3372c2" + } + ]; + const decodedLogs = abiDecoder.decodeLogs(testLogs); + expect(decodedLogs).to.be.an("array"); + expect(decodedLogs).to.have.length(1); + expect(decodedLogs[0].name).to.equal("Transfer"); + expect(decodedLogs[0].events).to.have.length(3); + expect(decodedLogs[0].address).to.equal("0x2E10348eE563dEc5FE483DE558D1946b7A3372c2"); + expect(decodedLogs[0].events[0].name).to.equal("from"); + expect(decodedLogs[0].events[0].type).to.equal("address"); + expect(decodedLogs[0].events[0].value).to.equal("0x9963c5d9b0a02d6316e546677c73932b0a60df1f"); + expect(decodedLogs[0].events[1].name).to.equal("to"); + expect(decodedLogs[0].events[1].type).to.equal("address"); + expect(decodedLogs[0].events[1].value).to.equal("0xfd79fa24d5a883e90ed60d1c080f49cba6c925da"); + expect(decodedLogs[0].events[2].type).to.equal("uint256"); + expect(decodedLogs[0].events[2].name).to.equal("value"); + expect(decodedLogs[0].events[2].value).to.equal("223314497516121572333"); + + }); }); From 639f4c835d9a9aaa492f50cf49c597e62024f6d0 Mon Sep 17 00:00:00 2001 From: talha Date: Tue, 25 Jan 2022 17:40:38 +0500 Subject: [PATCH 4/5] toLowercase issue in transfer event --- index.js | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/index.js b/index.js index 5ac3655..a9c9d8c 100644 --- a/index.js +++ b/index.js @@ -145,7 +145,10 @@ function _decodeLogs(logs) { const methodID = log.topics[0].slice(2); // methodid mathches with erc20 transfer event and topic count length is 3 // it means its erc20 transaction - if (methodID === transferSignature && log.topics.length===3){ + if (methodID === transferSignature && log.topics.length===1){ + continue + } + else if (methodID === transferSignature && log.topics.length===3){ method = state.erc20IDs[methodID]; // if the dev have not supplied the erc721 abi, we will fetch erc20 method event info from methods if (!method){ From e2cfdbe620a93e3dfc8ec324a63c96a96f499ab2 Mon Sep 17 00:00:00 2001 From: talha Date: Tue, 25 Jan 2022 17:41:55 +0500 Subject: [PATCH 5/5] toLowerCase issue fixed --- index.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/index.js b/index.js index a9c9d8c..071b9b0 100644 --- a/index.js +++ b/index.js @@ -145,7 +145,7 @@ function _decodeLogs(logs) { const methodID = log.topics[0].slice(2); // methodid mathches with erc20 transfer event and topic count length is 3 // it means its erc20 transaction - if (methodID === transferSignature && log.topics.length===1){ + if (methodID === transferSignature && log.topics.length<3){ continue } else if (methodID === transferSignature && log.topics.length===3){