@@ -13,33 +13,37 @@ import {
13
13
type EventType ,
14
14
type DecoderConfig ,
15
15
type Fallbacks ,
16
+ type NativeDecodingFunction ,
16
17
} from "./decoder.types" ;
17
18
import { encodeEventTopics , type Abi } from "viem" ;
18
19
19
20
export class GoldRushDecoder {
20
21
private static configs : DecoderConfig = { } ;
21
22
private static decoders : Decoders = { } ;
22
23
private static fallbacks : Fallbacks = { } ;
24
+ private static native_decoder : NativeDecodingFunction ;
23
25
private static decoding_functions : DecodingFunctions = [ ] ;
26
+ private static fallback_functions : DecodingFunctions = [ ] ;
27
+ private static fileExtension : "js" | "ts" =
28
+ process . env . NODE_ENV !== "test" ? "js" : "ts" ;
24
29
25
30
public static initDecoder = ( ) => {
26
31
console . info ( "Initializing GoldrushDecoder Service..." ) ;
27
32
28
33
const protocolsDirectoryPath : string = join ( __dirname , "/protocols" ) ;
29
34
const protocols = readdirSync ( protocolsDirectoryPath ) ;
30
35
let protocolsCount : number = 0 ;
36
+ let configsCount : number = 0 ;
31
37
for ( const protocol of protocols ) {
32
38
const protocolPath = join ( protocolsDirectoryPath , protocol ) ;
33
39
const files = readdirSync ( protocolPath ) ;
34
40
let configFile : string | null = null ,
35
41
decodersFile : string | null = null ;
36
42
files . forEach ( ( file ) => {
37
- const fileExtension =
38
- process . env . NODE_ENV !== "test" ? "js" : "ts" ;
39
- if ( file . endsWith ( `.configs.${ fileExtension } ` ) ) {
43
+ if ( file . endsWith ( `.configs.${ this . fileExtension } ` ) ) {
40
44
configFile = file ;
41
45
}
42
- if ( file . endsWith ( `.decoders.${ fileExtension } ` ) ) {
46
+ if ( file . endsWith ( `.decoders.${ this . fileExtension } ` ) ) {
43
47
decodersFile = file ;
44
48
}
45
49
} ) ;
@@ -54,6 +58,7 @@ export class GoldRushDecoder {
54
58
this . configs [ chain_name ] [ protocol_name ] [ address ] = {
55
59
is_factory : is_factory ,
56
60
} ;
61
+ configsCount ++ ;
57
62
}
58
63
) ;
59
64
require ( join ( protocolPath , decodersFile ) ) ;
@@ -62,37 +67,31 @@ export class GoldRushDecoder {
62
67
63
68
const fallbacksDirectoryPath : string = join ( __dirname , "/fallbacks" ) ;
64
69
const fallbacks = readdirSync ( fallbacksDirectoryPath ) ;
65
- let fallbacksCount : number = 0 ;
66
70
for ( const fallback of fallbacks ) {
67
71
const fallbackPath = join ( fallbacksDirectoryPath , fallback ) ;
68
72
const files = readdirSync ( fallbackPath ) ;
69
73
let fallbackFile : string | null = null ;
70
74
files . forEach ( ( file ) => {
71
- const fileExtension =
72
- process . env . NODE_ENV !== "test" ? "js" : "ts" ;
73
- if ( file . endsWith ( `.fallback.${ fileExtension } ` ) ) {
75
+ if ( file . endsWith ( `.fallback.${ this . fileExtension } ` ) ) {
74
76
fallbackFile = file ;
75
77
}
76
78
} ) ;
77
79
if ( fallbackFile ) {
78
- fallbacksCount ++ ;
79
80
require ( join ( fallbackPath , fallbackFile ) ) ;
80
81
}
81
82
}
82
83
83
- const decodersCount = Object . keys ( this . decoding_functions ) . length ;
84
- const configsCount = Object . values ( this . configs ) . reduce (
85
- ( chainCount , chain ) => {
86
- return (
87
- chainCount +
88
- Object . values ( chain ) . reduce ( ( addressCount , protocol ) => {
89
- return addressCount + Object . keys ( protocol ) . length ;
90
- } , 0 )
91
- ) ;
92
- } ,
93
- 0
84
+ const nativeDecoderPath : string = join (
85
+ __dirname ,
86
+ "native" ,
87
+ `native.decoder.${ this . fileExtension } `
94
88
) ;
89
+ require ( join ( nativeDecoderPath ) ) ;
90
+
91
+ const decodersCount = this . decoding_functions . length ;
92
+ const fallbacksCount = this . fallback_functions . length ;
95
93
94
+ console . info ( "1 native decoder added" ) ;
96
95
console . info ( `${ protocolsCount . toLocaleString ( ) } protocols found` ) ;
97
96
console . info ( `${ configsCount . toLocaleString ( ) } configs generated` ) ;
98
97
console . info ( `${ decodersCount . toLocaleString ( ) } decoders generated` ) ;
@@ -124,10 +123,16 @@ export class GoldRushDecoder {
124
123
}
125
124
Object . keys ( this . configs [ chain_name ] [ protocol ] ) . forEach (
126
125
( address ) => {
127
- this . decoders [ chain_name ] ??= { } ;
128
- this . decoders [ chain_name ] [ address ] ??= { } ;
129
- this . decoders [ chain_name ] [ address ] [ topic0_hash ] =
130
- decoding_function_index ;
126
+ const lowercaseChainName =
127
+ chain_name . toLowerCase ( ) as Chain ;
128
+ const lowercaseAddress = address . toLowerCase ( ) ;
129
+ const lowercaseTopic0Hash = topic0_hash . toLowerCase ( ) ;
130
+
131
+ this . decoders [ lowercaseChainName ] ??= { } ;
132
+ this . decoders [ lowercaseChainName ] [ lowercaseAddress ] ??= { } ;
133
+ this . decoders [ lowercaseChainName ] [ lowercaseAddress ] [
134
+ lowercaseTopic0Hash
135
+ ] = decoding_function_index ;
131
136
}
132
137
) ;
133
138
} ) ;
@@ -142,10 +147,15 @@ export class GoldRushDecoder {
142
147
abi : abi ,
143
148
eventName : event_name ,
144
149
} ) ;
145
- this . decoding_functions . push ( decoding_function ) ;
146
- const decoding_function_index : number =
147
- this . decoding_functions . length - 1 ;
148
- this . fallbacks [ topic0_hash ] = decoding_function_index ;
150
+ const lowercaseTopic0Hash = topic0_hash . toLowerCase ( ) ;
151
+ this . fallback_functions . push ( decoding_function ) ;
152
+ const fallback_function_index : number =
153
+ this . fallback_functions . length - 1 ;
154
+ this . fallbacks [ lowercaseTopic0Hash ] = fallback_function_index ;
155
+ } ;
156
+
157
+ public static native = ( native_decoder : NativeDecodingFunction ) => {
158
+ this . native_decoder = native_decoder ;
149
159
} ;
150
160
151
161
public static decode = async (
@@ -155,26 +165,46 @@ export class GoldRushDecoder {
155
165
) => {
156
166
const covalent_client = new CovalentClient ( covalent_api_key ) ;
157
167
const events : EventType [ ] = [ ] ;
158
- const logs = ( tx . log_events ?? [ ] ) . reverse ( ) ;
159
- for ( const log of logs ) {
160
- const {
161
- raw_log_topics : [ topic0_hash ] ,
162
- sender_address : contract_address ,
163
- // !ERROR: add factory_contract_address in the log_event(s)
164
- // factory_contract_address,
165
- } = log ;
166
- const decoding_index =
167
- // !ERROR: add factory_contract_address in the log_event(s)
168
- // factory_contract_address ||
169
- this . decoders [ chain_name ] [ contract_address ] ?. [ topic0_hash ] ;
170
- const fallback_index = this . fallbacks [ topic0_hash ] ;
171
- if ( decoding_index !== undefined || fallback_index !== undefined ) {
172
- const event = await this . decoding_functions [
173
- decoding_index ?? fallback_index
174
- ] ( log , tx , chain_name , covalent_client ) ;
175
- events . push ( event ) ;
176
- }
168
+ if ( tx . value ) {
169
+ const nativeEvent = this . native_decoder ( tx ) ;
170
+ events . push ( nativeEvent ) ;
177
171
}
178
- return events ;
172
+
173
+ const decodedEvents = await Promise . all (
174
+ ( tx . log_events ?? [ ] ) . map ( ( log ) => {
175
+ const {
176
+ raw_log_topics : [ topic0_hash ] ,
177
+ sender_address,
178
+ sender_factory_address,
179
+ } = log ;
180
+ const lowercaseChainName = chain_name . toLowerCase ( ) as Chain ;
181
+ const lowercaseSenderAddress = sender_address ?. toLowerCase ( ) ;
182
+ const lowercaseSenderFactoryAddress =
183
+ sender_factory_address ?. toLowerCase ( ) ;
184
+ const lowercaseTopic0Hash = topic0_hash ?. toLowerCase ( ) ;
185
+
186
+ const decoding_index =
187
+ this . decoders [ lowercaseChainName ] ?. [
188
+ lowercaseSenderAddress
189
+ ] ?. [ lowercaseTopic0Hash ] ??
190
+ this . decoders [ lowercaseChainName ] ?. [
191
+ lowercaseSenderFactoryAddress
192
+ ] ?. [ lowercaseTopic0Hash ] ;
193
+ const fallback_index = this . fallbacks [ lowercaseTopic0Hash ] ;
194
+
195
+ const logFunction =
196
+ decoding_index !== undefined
197
+ ? this . decoding_functions [ decoding_index ]
198
+ : fallback_index !== undefined
199
+ ? this . fallback_functions [ fallback_index ]
200
+ : null ;
201
+
202
+ return logFunction
203
+ ? logFunction ( log , tx , chain_name , covalent_client )
204
+ : null ;
205
+ } )
206
+ ) ;
207
+
208
+ return events . concat ( decodedEvents . filter ( Boolean ) as EventType [ ] ) ;
179
209
} ;
180
210
}
0 commit comments