@@ -42,113 +42,61 @@ import {
42
42
Bytes8Ty ,
43
43
Bytes9Ty ,
44
44
BytesTy ,
45
- ConsoleLogs ,
46
45
Int256Ty ,
47
46
StringTy ,
48
47
Uint256Ty ,
48
+ CONSOLE_LOG_SIGNATURES ,
49
49
} from "./logger" ;
50
- import {
51
- EvmMessageTrace ,
52
- isCallTrace ,
53
- isEvmStep ,
54
- isPrecompileTrace ,
55
- MessageTrace ,
56
- } from "./message-trace" ;
57
50
58
- const CONSOLE_ADDRESS = "0x000000000000000000636F6e736F6c652e6c6f67" ; // toHex("console.log")
59
51
const REGISTER_SIZE = 32 ;
60
52
61
- // eslint-disable-next-line @typescript-eslint/no-empty-interface
62
- interface ConsoleLogArray extends Array < ConsoleLogEntry > { }
63
-
64
- export type ConsoleLogEntry = string | ConsoleLogArray ;
65
-
66
- // eslint-disable-next-line @typescript-eslint/no-redeclare
67
- export type ConsoleLogs = ConsoleLogEntry [ ] ;
53
+ /** The decoded string representation of the arguments supplied to console.log */
54
+ export type ConsoleLogArgs = string [ ] ;
55
+ export type ConsoleLogs = ConsoleLogArgs [ ] ;
68
56
69
57
export class ConsoleLogger {
70
- private readonly _consoleLogs : {
71
- [ key : number ] : string [ ] ;
72
- } = { } ;
73
-
74
- constructor ( ) {
75
- this . _consoleLogs = ConsoleLogs ;
76
- }
77
-
78
- public getLogMessages ( maybeDecodedMessageTrace : MessageTrace ) : string [ ] {
79
- return this . getExecutionLogs ( maybeDecodedMessageTrace ) . map (
80
- consoleLogToString
81
- ) ;
82
- }
83
-
84
- public getExecutionLogs (
85
- maybeDecodedMessageTrace : MessageTrace
86
- ) : ConsoleLogs [ ] {
87
- if ( isPrecompileTrace ( maybeDecodedMessageTrace ) ) {
88
- return [ ] ;
89
- }
90
-
91
- const logs : ConsoleLogs [ ] = [ ] ;
92
- this . _collectExecutionLogs ( maybeDecodedMessageTrace , logs ) ;
93
- return logs ;
94
- }
95
-
96
- private _collectExecutionLogs ( trace : EvmMessageTrace , logs : ConsoleLogs ) {
97
- for ( const messageTrace of trace . steps ) {
98
- if ( isEvmStep ( messageTrace ) || isPrecompileTrace ( messageTrace ) ) {
99
- continue ;
100
- }
101
-
102
- if (
103
- isCallTrace ( messageTrace ) &&
104
- bufferToHex ( messageTrace . address ) === CONSOLE_ADDRESS . toLowerCase ( )
105
- ) {
106
- const log = this . _maybeConsoleLog ( Buffer . from ( messageTrace . calldata ) ) ;
107
- if ( log !== undefined ) {
108
- logs . push ( log ) ;
109
- }
110
-
111
- continue ;
112
- }
113
-
114
- this . _collectExecutionLogs ( messageTrace , logs ) ;
115
- }
116
- }
117
-
118
58
/**
119
59
* Temporary code to print console.sol messages that come from EDR
120
60
*/
121
- public getDecodedLogs ( messages : Buffer [ ] ) : string [ ] {
61
+ public static getDecodedLogs ( messages : Buffer [ ] ) : string [ ] {
122
62
const logs : string [ ] = [ ] ;
123
63
124
64
for ( const message of messages ) {
125
- const log = this . _maybeConsoleLog ( message ) ;
65
+ const log = ConsoleLogger . _maybeConsoleLog ( message ) ;
126
66
if ( log !== undefined ) {
127
- logs . push ( consoleLogToString ( log ) ) ;
67
+ logs . push ( ConsoleLogger . format ( log ) ) ;
128
68
}
129
69
}
130
70
131
71
return logs ;
132
72
}
133
73
134
- private _maybeConsoleLog ( calldata : Buffer ) : ConsoleLogs | undefined {
135
- const sig = bytesToInt ( calldata . slice ( 0 , 4 ) ) ;
74
+ /**
75
+ * Returns a formatted string using the first argument as a `printf`-like
76
+ * format string which can contain zero or more format specifiers.
77
+ *
78
+ * If there are more arguments passed than the number of specifiers, the
79
+ * extra arguments are concatenated to the returned string, separated by spaces.
80
+ */
81
+ public static format ( args : ConsoleLogArgs = [ ] ) : string {
82
+ return util . format ( ...args ) ;
83
+ }
84
+
85
+ private static _maybeConsoleLog (
86
+ calldata : Buffer
87
+ ) : ConsoleLogArgs | undefined {
88
+ const selector = bytesToInt ( calldata . slice ( 0 , 4 ) ) ;
136
89
const parameters = calldata . slice ( 4 ) ;
137
90
138
- const types = this . _consoleLogs [ sig ] ;
139
- if ( types === undefined ) {
91
+ const argTypes = CONSOLE_LOG_SIGNATURES [ selector ] ;
92
+ if ( argTypes === undefined ) {
140
93
return ;
141
94
}
142
95
143
- const consoleLogs = this . _decode ( parameters , types ) ;
96
+ const decodedArgs = ConsoleLogger . _decode ( parameters , argTypes ) ;
144
97
145
- this . _replaceNumberFormatSpecifiers ( consoleLogs ) ;
146
-
147
- return consoleLogs ;
148
- }
149
-
150
- private _replaceNumberFormatSpecifiers ( consoleLogs : ConsoleLogs ) {
151
98
/**
99
+ * The first argument is interpreted as the format string, which may need adjusting.
152
100
* Replace the occurrences of %d and %i with %s. This is necessary because if the arguments passed are numbers,
153
101
* they could be too large to be formatted as a Number or an Integer, so it is safer to use a String.
154
102
* %d and %i are replaced only if there is an odd number of % before the d or i.
@@ -160,15 +108,18 @@ export class ConsoleLogger {
160
108
* (?<!%) negative look-behind to make this work.
161
109
* The (?:) is just to avoid capturing that inner group.
162
110
*/
163
- if ( consoleLogs . length > 0 && typeof consoleLogs [ 0 ] === "string" ) {
164
- consoleLogs [ 0 ] = consoleLogs [ 0 ] . replace (
111
+ if ( decodedArgs . length > 0 ) {
112
+ decodedArgs [ 0 ] = decodedArgs [ 0 ] . replace (
165
113
/ ( (?< ! % ) (?: % % ) * ) ( % [ d i ] ) / g,
166
114
"$1%s"
167
115
) ;
168
116
}
117
+
118
+ return decodedArgs ;
169
119
}
170
120
171
- private _decode ( data : Buffer , types : string [ ] ) : ConsoleLogs {
121
+ /** Decodes parameters from `data` according to `types` into their string representation. */
122
+ private static _decode ( data : Buffer , types : string [ ] ) : string [ ] {
172
123
return types . map ( ( type , i ) => {
173
124
const position : number = i * 32 ;
174
125
switch ( types [ i ] ) {
@@ -282,16 +233,3 @@ export class ConsoleLogger {
282
233
} ) ;
283
234
}
284
235
}
285
-
286
- export function consoleLogToString ( log : ConsoleLogs ) : string {
287
- if ( log === undefined ) {
288
- return "" ;
289
- }
290
-
291
- // special case for console.log()
292
- if ( log . length === 0 ) {
293
- return "" ;
294
- }
295
-
296
- return util . format ( log [ 0 ] , ...log . slice ( 1 ) ) ;
297
- }
0 commit comments