Skip to content

Commit fd78bb9

Browse files
committed
feat: consistent stack trace and only export ErrorLogger
1 parent 0489ec8 commit fd78bb9

File tree

4 files changed

+45
-42
lines changed

4 files changed

+45
-42
lines changed

packages/util/src/errors.ts

Lines changed: 28 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
export enum ErrorCode {
1+
enum ErrorCode {
22
INVALID_PARAM = 'INVALID_PARAM',
33
UNKNOWN_ERROR = 'UNKNOWN_ERROR',
44
}
@@ -16,7 +16,7 @@ interface UnknownError extends GeneralError<ErrorCode.UNKNOWN_ERROR> {
1616
}
1717

1818
// Convert an ErrorCode into its Typed Error
19-
export type CodedGeneralError<T> = T extends ErrorCode.INVALID_PARAM
19+
type CodedGeneralError<T> = T extends ErrorCode.INVALID_PARAM
2020
? InvalidParamError
2121
: T extends ErrorCode.UNKNOWN_ERROR
2222
? UnknownError
@@ -44,47 +44,50 @@ export class ErrorLogger {
4444
static errors = ErrorCode
4545

4646
makeError<T>(codedError: CodedGeneralError<T>): Error {
47-
let { message } = codedError
47+
const { code, message, ...params } = codedError
4848
const messageDetails: Array<string> = []
4949

50-
if (isInvalidParamError(codedError) && typeof codedError.param !== 'undefined') {
50+
if (isInvalidParamError(codedError) && typeof params.param !== 'undefined') {
5151
messageDetails.push(`Invalid param=${codedError.param}`)
5252
}
5353

5454
if (isUnknownError(codedError)) {
55-
Object.keys(codedError)
56-
.filter((key) => ['message', 'code', 'stack'].includes(key))
57-
.forEach((key) => {
58-
const value = codedError[key]
59-
try {
60-
messageDetails.push(key + '=' + JSON.stringify(value))
61-
} catch {
62-
messageDetails.push(key + '=' + JSON.stringify(codedError[key].toString()))
63-
}
64-
})
55+
Object.keys(params).forEach((key) => {
56+
const value = codedError[key]
57+
try {
58+
messageDetails.push(key + '=' + JSON.stringify(value))
59+
} catch {
60+
messageDetails.push(key + '=' + JSON.stringify(codedError[key].toString()))
61+
}
62+
})
6563
}
6664

67-
messageDetails.push(`code=${codedError.code}`)
65+
messageDetails.push(`code=${code}`)
66+
67+
let errorMessage = message ?? ''
6868

6969
if (messageDetails.length) {
70-
message += ' | Details: ' + messageDetails.join(', ')
70+
errorMessage += ' | Details: ' + messageDetails.join(', ')
7171
}
7272

73-
const error = new Error(message) as CodedGeneralError<T>
73+
const error = new Error(errorMessage) as CodedGeneralError<T>
7474
error.code = codedError.code
7575

76-
Object.keys(codedError)
77-
.filter((key) => key !== 'message' && key !== 'code')
78-
.forEach((key) => {
79-
const typedKey = key as keyof typeof codedError
80-
error[typedKey] = codedError[typedKey]
81-
})
76+
Object.keys(params).forEach((key) => {
77+
const typedKey = key as keyof typeof codedError
78+
error[typedKey] = codedError[typedKey]
79+
})
80+
81+
Error.captureStackTrace(error, this.throwError)
8282

8383
throw error
8484
}
8585

86-
throwError<T extends ErrorCode>(code?: T, params?: Omit<CodedGeneralError<T>, 'code'>): never {
87-
throw this.makeError({
86+
throwError<T extends ErrorCode>(
87+
code?: T,
88+
params?: Omit<CodedGeneralError<T>, 'code' | 'stack'>
89+
): void {
90+
this.makeError({
8891
code: code ?? ErrorCode.UNKNOWN_ERROR,
8992
...params,
9093
} as CodedGeneralError<T>)

packages/util/test/errors.spec.ts

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import tape from 'tape'
2-
import { ErrorCode, ErrorLogger } from '../src/errors'
2+
import { ErrorLogger } from '../src/errors'
33

44
tape('ErrorLogger', (t) => {
55
const errorLog = new ErrorLogger()
@@ -13,14 +13,14 @@ tape('ErrorLogger', (t) => {
1313
error = e
1414
}
1515

16-
st.equal(error.code, ErrorCode.UNKNOWN_ERROR)
16+
st.equal(error.code, ErrorLogger.errors.UNKNOWN_ERROR)
1717
st.end()
1818
}),
1919
t.test('should populate an error with UNKNOWN_ERROR code with all provided params', (st) => {
2020
let error: any
2121

2222
try {
23-
errorLog.throwError(ErrorCode.UNKNOWN_ERROR, {
23+
errorLog.throwError(ErrorLogger.errors.UNKNOWN_ERROR, {
2424
errorInfo1: 'Information on the error',
2525
errorInfo2: 'More information on the error',
2626
})
@@ -36,22 +36,22 @@ tape('ErrorLogger', (t) => {
3636
let error: any
3737

3838
try {
39-
errorLog.throwError(ErrorCode.UNKNOWN_ERROR, {
39+
errorLog.throwError(ErrorLogger.errors.UNKNOWN_ERROR, {
4040
errorInfo1: 'Information on the error',
4141
errorInfo2: 'More information on the error',
4242
})
4343
} catch (e) {
4444
error = e
4545
}
4646

47-
st.equal(error.code, ErrorCode.UNKNOWN_ERROR)
47+
st.equal(error.code, ErrorLogger.errors.UNKNOWN_ERROR)
4848
st.end()
4949
}),
5050
t.test('should add all error params to error message details', (st) => {
5151
let error: any
5252

5353
try {
54-
errorLog.throwError(ErrorCode.UNKNOWN_ERROR, {
54+
errorLog.throwError(ErrorLogger.errors.UNKNOWN_ERROR, {
5555
errorInfo1: 'Information on the error',
5656
errorInfo2: 'More information on the error',
5757
})
@@ -69,7 +69,7 @@ tape('ErrorLogger', (t) => {
6969
let error: any
7070

7171
try {
72-
errorLog.throwError(ErrorCode.UNKNOWN_ERROR, {
72+
errorLog.throwError(ErrorLogger.errors.UNKNOWN_ERROR, {
7373
message: 'Error Message',
7474
errorInfo1: 'Information on the error',
7575
errorInfo2: 'More information on the error',
@@ -88,7 +88,7 @@ tape('ErrorLogger', (t) => {
8888
let error: any
8989

9090
try {
91-
errorLog.throwError(ErrorCode.INVALID_PARAM, {
91+
errorLog.throwError(ErrorLogger.errors.INVALID_PARAM, {
9292
param: 'difficulty',
9393
})
9494
} catch (e) {
@@ -102,7 +102,7 @@ tape('ErrorLogger', (t) => {
102102
let error: any
103103

104104
try {
105-
errorLog.throwError(ErrorCode.INVALID_PARAM, {
105+
errorLog.throwError(ErrorLogger.errors.INVALID_PARAM, {
106106
message: 'Gas limit higher than maximum',
107107
param: 'gasLimit',
108108
})

packages/vm/src/runBlock.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { debug as createDebugLogger } from 'debug'
22
import { BaseTrie as Trie } from 'merkle-patricia-tree'
3-
import { Account, Address, BN, errorLog, ErrorCode, intToBuffer, rlp } from 'ethereumjs-util'
3+
import { Account, Address, BN, errorLog, ErrorLogger, intToBuffer, rlp } from 'ethereumjs-util'
44
import { Block } from '@ethereumjs/block'
55
import { ConsensusType } from '@ethereumjs/common'
66
import VM from './index'
@@ -202,7 +202,7 @@ export default async function runBlock(this: VM, opts: RunBlockOpts): Promise<Ru
202202
)
203203
}
204204
const message = _errorMsg('invalid receiptTrie', this, block)
205-
errorLog.throwError(ErrorCode.INVALID_PARAM, {
205+
errorLog.throwError(ErrorLogger.errors.INVALID_PARAM, {
206206
message,
207207
param: 'receiptTrie',
208208
})
@@ -216,7 +216,7 @@ export default async function runBlock(this: VM, opts: RunBlockOpts): Promise<Ru
216216
)
217217
}
218218
const message = _errorMsg('invalid bloom', this, block)
219-
errorLog.throwError(ErrorCode.INVALID_PARAM, {
219+
errorLog.throwError(ErrorLogger.errors.INVALID_PARAM, {
220220
message,
221221
param: 'bloom',
222222
})
@@ -226,7 +226,7 @@ export default async function runBlock(this: VM, opts: RunBlockOpts): Promise<Ru
226226
debug(`Invalid gasUsed received=${result.gasUsed} expected=${block.header.gasUsed}`)
227227
}
228228
const message = _errorMsg('invalid gasUsed', this, block)
229-
errorLog.throwError(ErrorCode.INVALID_PARAM, {
229+
errorLog.throwError(ErrorLogger.errors.INVALID_PARAM, {
230230
message,
231231
param: 'gasUsed',
232232
})
@@ -240,7 +240,7 @@ export default async function runBlock(this: VM, opts: RunBlockOpts): Promise<Ru
240240
)
241241
}
242242
const message = _errorMsg('invalid block stateRoot', this, block)
243-
errorLog.throwError(ErrorCode.INVALID_PARAM, {
243+
errorLog.throwError(ErrorLogger.errors.INVALID_PARAM, {
244244
message,
245245
param: 'stateRoot',
246246
})
@@ -290,7 +290,7 @@ async function applyBlock(this: VM, block: Block, opts: RunBlockOpts) {
290290
if (!opts.skipBlockValidation) {
291291
if (block.header.gasLimit.gte(new BN('8000000000000000', 16))) {
292292
const message = _errorMsg('Invalid block with gas limit greater than (2^63 - 1)', this, block)
293-
errorLog.throwError(ErrorCode.INVALID_PARAM, {
293+
errorLog.throwError(ErrorLogger.errors.INVALID_PARAM, {
294294
message,
295295
param: 'gasLimit',
296296
})

packages/vm/tests/api/runBlock.spec.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import tape from 'tape'
2-
import { Address, BN, rlp, KECCAK256_RLP, Account, ErrorCode } from 'ethereumjs-util'
2+
import { Address, BN, rlp, KECCAK256_RLP, Account, ErrorLogger } from 'ethereumjs-util'
33
import Common, { Chain, Hardfork } from '@ethereumjs/common'
44
import { Block } from '@ethereumjs/block'
55
import {
@@ -212,7 +212,7 @@ tape('runBlock() -> API parameter usage/data errors', async (t) => {
212212
await vm
213213
.runBlock({ block })
214214
.then(() => t.fail('should have returned error'))
215-
.catch((e) => t.ok(e.code === ErrorCode.INVALID_PARAM && e.param === 'gasLimit'))
215+
.catch((e) => t.ok(e.code === ErrorLogger.errors.INVALID_PARAM && e.param === 'gasLimit'))
216216
})
217217

218218
t.test('should fail when block validation fails', async (t) => {

0 commit comments

Comments
 (0)