Skip to content

Commit f2cba9e

Browse files
committed
chore: lintfix
fix: jests related to toError and fromError
1 parent b091f73 commit f2cba9e

File tree

9 files changed

+785
-48
lines changed

9 files changed

+785
-48
lines changed

package-lock.json

Lines changed: 736 additions & 7 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/RPCClient.ts

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ import * as rpcUtils from './utils/utils';
2626
import { promise } from './utils';
2727
import { ErrorRPCStreamEnded, never } from './errors';
2828
import * as events from './events';
29+
import { toError } from './utils/utils';
2930

3031
const timerCleanupReasonSymbol = Symbol('timerCleanUpReasonSymbol');
3132

@@ -82,7 +83,6 @@ class RPCClient<M extends ClientManifest> {
8283
streamKeepAliveTimeoutTime?: number;
8384
logger?: Logger;
8485
idGen: IdGen;
85-
toError?: (errorData, metadata?: JSONValue) => ErrorRPCRemote<unknown>;
8686
}) {
8787
logger.info(`Creating ${this.name}`);
8888
const rpcClient = new this({
@@ -107,7 +107,6 @@ class RPCClient<M extends ClientManifest> {
107107
Uint8Array
108108
>;
109109
protected callerTypes: Record<string, HandlerType>;
110-
toError: (errorData: any, metadata?: JSONValue) => Error;
111110
public registerOnTimeoutCallback(callback: () => void) {
112111
this.onTimeoutCallback = callback;
113112
}
@@ -144,7 +143,6 @@ class RPCClient<M extends ClientManifest> {
144143
streamKeepAliveTimeoutTime,
145144
logger,
146145
idGen = () => Promise.resolve(null),
147-
toError,
148146
}: {
149147
manifest: M;
150148
streamFactory: StreamFactory;
@@ -157,15 +155,13 @@ class RPCClient<M extends ClientManifest> {
157155
streamKeepAliveTimeoutTime: number;
158156
logger: Logger;
159157
idGen: IdGen;
160-
toError?: (errorData, metadata?: JSONValue) => ErrorRPCRemote<unknown>;
161158
}) {
162159
this.idGen = idGen;
163160
this.callerTypes = rpcUtils.getHandlerTypes(manifest);
164161
this.streamFactory = streamFactory;
165162
this.middlewareFactory = middlewareFactory;
166163
this.streamKeepAliveTimeoutTime = streamKeepAliveTimeoutTime;
167164
this.logger = logger;
168-
this.toError = toError || rpcUtils.toError;
169165
}
170166

171167
public async destroy({
@@ -550,7 +546,7 @@ class RPCClient<M extends ClientManifest> {
550546
...(rpcStream.meta ?? {}),
551547
command: method,
552548
};
553-
throw this.toError(messageValue.error.data, metadata);
549+
throw toError(messageValue.error.data, metadata);
554550
}
555551
leadingMessage = messageValue;
556552
} catch (e) {

src/RPCServer.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -352,6 +352,7 @@ class RPCServer extends EventTarget {
352352
code: e.exitCode ?? JSONRPCErrorCode.InternalError,
353353
message: e.description ?? '',
354354
data: JSON.stringify(this.fromError(e), this.replacer),
355+
type: e.type,
355356
};
356357
const rpcErrorMessage: JSONRPCResponseError = {
357358
jsonrpc: '2.0',
@@ -616,6 +617,7 @@ class RPCServer extends EventTarget {
616617
code: e.exitCode ?? JSONRPCErrorCode.InternalError,
617618
message: e.description ?? '',
618619
data: JSON.stringify(this.fromError(e), this.replacer),
620+
type: e.type,
619621
};
620622
const rpcErrorMessage: JSONRPCResponseError = {
621623
jsonrpc: '2.0',

src/errors/errors.ts

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -30,10 +30,12 @@ interface RPCError extends Error {
3030
}
3131
class ErrorRPC<T> extends AbstractError<T> implements RPCError {
3232
private _description: string = 'Generic Error';
33+
type: string;
3334
constructor(message?: string) {
3435
super(message);
36+
this.type = this.constructor.name;
3537
}
36-
code?: number;
38+
code: number;
3739

3840
get description(): string {
3941
return this._description;
@@ -49,6 +51,7 @@ class ErrorRPCDestroyed<T> extends ErrorRPC<T> {
4951
super(message); // Call the parent constructor
5052
this.description = 'Rpc is destroyed'; // Set the specific description
5153
this.code = JSONRPCErrorCode.MethodNotFound;
54+
this.type = this.constructor.name;
5255
}
5356
}
5457

@@ -59,6 +62,7 @@ class ErrorRPCParse<T> extends ErrorRPC<T> {
5962
super(message); // Call the parent constructor
6063
this.description = 'Failed to parse Buffer stream'; // Set the specific description
6164
this.code = JSONRPCErrorCode.ParseError;
65+
this.type = this.constructor.name;
6266
}
6367
}
6468

@@ -67,6 +71,7 @@ class ErrorRPCStopping<T> extends ErrorRPC<T> {
6771
super(message); // Call the parent constructor
6872
this.description = 'Rpc is stopping'; // Set the specific description
6973
this.code = JSONRPCErrorCode.RPCStopping;
74+
this.type = this.constructor.name;
7075
}
7176
}
7277

@@ -78,27 +83,31 @@ class ErrorRPCHandlerFailed<T> extends ErrorRPC<T> {
7883
super(message); // Call the parent constructor
7984
this.description = 'Failed to handle stream'; // Set the specific description
8085
this.code = JSONRPCErrorCode.HandlerNotFound;
86+
this.type = this.constructor.name;
8187
}
8288
}
8389
class ErrorRPCCallerFailed<T> extends ErrorRPC<T> {
8490
constructor(message?: string, options?: { cause: Error }) {
8591
super(message); // Call the parent constructor
8692
this.description = 'Failed to call stream'; // Set the specific description
8793
this.code = JSONRPCErrorCode.MissingCaller;
94+
this.type = this.constructor.name;
8895
}
8996
}
9097
class ErrorMissingCaller<T> extends ErrorRPC<T> {
9198
constructor(message?: string, options?: { cause: Error }) {
9299
super(message); // Call the parent constructor
93100
this.description = 'Header information is missing'; // Set the specific description
94101
this.code = JSONRPCErrorCode.MissingCaller;
102+
this.type = this.constructor.name;
95103
}
96104
}
97105
class ErrorMissingHeader<T> extends ErrorRPC<T> {
98106
constructor(message?: string, options?: { cause: Error }) {
99107
super(message); // Call the parent constructor
100108
this.description = 'Header information is missing'; // Set the specific description
101109
this.code = JSONRPCErrorCode.MissingHeader;
110+
this.type = this.constructor.name;
102111
}
103112
}
104113

@@ -107,18 +116,20 @@ class ErrorHandlerAborted<T> extends ErrorRPC<T> {
107116
super(message); // Call the parent constructor
108117
this.description = 'Handler Aborted Stream.'; // Set the specific description
109118
this.code = JSONRPCErrorCode.HandlerAborted;
119+
this.type = this.constructor.name;
110120
}
111121
}
112122
class ErrorRPCMessageLength<T> extends ErrorRPC<T> {
113123
static description = 'RPC Message exceeds maximum size';
114-
code? = JSONRPCErrorCode.RPCMessageLength;
124+
code = JSONRPCErrorCode.RPCMessageLength;
115125
}
116126

117127
class ErrorRPCMissingResponse<T> extends ErrorRPC<T> {
118128
constructor(message?: string) {
119129
super(message);
120130
this.description = 'Stream ended before response';
121131
this.code = JSONRPCErrorCode.RPCMissingResponse;
132+
this.type = this.constructor.name;
122133
}
123134
}
124135

@@ -130,6 +141,7 @@ class ErrorRPCOutputStreamError<T> extends ErrorRPC<T> {
130141
super(message);
131142
this.description = 'Output stream failed, unable to send data';
132143
this.code = JSONRPCErrorCode.RPCOutputStreamError;
144+
this.type = this.constructor.name;
133145
}
134146
}
135147

@@ -143,6 +155,8 @@ class ErrorRPCRemote<T> extends ErrorRPC<T> {
143155
this.metadata = metadata;
144156
this.code = JSONRPCErrorCode.RPCRemote;
145157
this.data = options?.data;
158+
this.type = this.constructor.name;
159+
this.message = message || ErrorRPCRemote.message;
146160
}
147161

148162
public static fromJSON<T extends Class<any>>(
@@ -188,6 +202,7 @@ class ErrorRPCStreamEnded<T> extends ErrorRPC<T> {
188202
super(message);
189203
this.description = 'Handled stream has ended';
190204
this.code = JSONRPCErrorCode.RPCStreamEnded;
205+
this.type = this.constructor.name;
191206
}
192207
}
193208

@@ -196,6 +211,7 @@ class ErrorRPCTimedOut<T> extends ErrorRPC<T> {
196211
super(message);
197212
this.description = 'RPC handler has timed out';
198213
this.code = JSONRPCErrorCode.RPCTimedOut;
214+
this.type = this.constructor.name;
199215
}
200216
}
201217

@@ -204,6 +220,7 @@ class ErrorUtilsUndefinedBehaviour<T> extends ErrorRPC<T> {
204220
super(message);
205221
this.description = 'You should never see this error';
206222
this.code = JSONRPCErrorCode.MethodNotFound;
223+
this.type = this.constructor.name;
207224
}
208225
}
209226
export function never(): never {
@@ -217,27 +234,28 @@ class ErrorRPCMethodNotImplemented<T> extends ErrorRPC<T> {
217234
this.description =
218235
'This abstract method must be implemented in a derived class';
219236
this.code = JSONRPCErrorCode.MethodNotFound;
237+
this.type = this.constructor.name;
220238
}
221239
}
222240

223241
class ErrorRPCConnectionLocal<T> extends ErrorRPC<T> {
224242
static description = 'RPC Connection local error';
225-
code? = JSONRPCErrorCode.RPCConnectionLocal;
243+
code = JSONRPCErrorCode.RPCConnectionLocal;
226244
}
227245

228246
class ErrorRPCConnectionPeer<T> extends ErrorRPC<T> {
229247
static description = 'RPC Connection peer error';
230-
code? = JSONRPCErrorCode.RPCConnectionPeer;
248+
code = JSONRPCErrorCode.RPCConnectionPeer;
231249
}
232250

233251
class ErrorRPCConnectionKeepAliveTimeOut<T> extends ErrorRPC<T> {
234252
static description = 'RPC Connection keep alive timeout';
235-
code? = JSONRPCErrorCode.RPCConnectionKeepAliveTimeOut;
253+
code = JSONRPCErrorCode.RPCConnectionKeepAliveTimeOut;
236254
}
237255

238256
class ErrorRPCConnectionInternal<T> extends ErrorRPC<T> {
239257
static description = 'RPC Connection internal error';
240-
code? = JSONRPCErrorCode.RPCConnectionInternal;
258+
code = JSONRPCErrorCode.RPCConnectionInternal;
241259
}
242260

243261
export {

src/types.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@ import type { ServerCaller } from './callers';
77
import type { ClientCaller } from './callers';
88
import type { UnaryCaller } from './callers';
99
import type Handler from './handlers/Handler';
10+
import type { ErrorRPC } from '@/errors';
11+
import { ErrorRPCRemote } from '@/errors';
1012

1113
/**
1214
* This is the type for the IdGenFunction. It is used to generate the request
@@ -130,6 +132,8 @@ type JSONRPCError = {
130132
* The value of this member is defined by the Server (e.g. detailed error information, nested errors etc.).
131133
*/
132134
data?: JSONValue;
135+
136+
type: string | ErrorRPC<any>;
133137
};
134138

135139
/**

src/utils/utils.ts

Lines changed: 5 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -224,20 +224,15 @@ function parseJSONRPCMessage<T extends JSONValue>(
224224
*/
225225
function fromError(error: ErrorRPC<any>, id?: any): JSONValue {
226226
const data: { [key: string]: JSONValue } = {
227+
errorCode: error.code,
227228
message: error.message,
228-
description: error.description,
229229
data: error.data,
230+
type: error.constructor.name,
230231
};
231-
if (error.code !== undefined) {
232-
data.code = error.code;
233-
}
234232
return {
235-
jsonrpc: '2.0',
236233
error: {
237-
type: error.name,
238-
...data,
234+
data,
239235
},
240-
id: id !== undefined ? id : null,
241236
};
242237
}
243238

@@ -376,11 +371,9 @@ function toError(errorResponse: any, metadata?: any): ErrorRPCRemote<any> {
376371
if (
377372
typeof errorResponse !== 'object' ||
378373
errorResponse === null ||
379-
!('error' in errorResponse) ||
380-
!('type' in errorResponse.error) ||
381-
!('message' in errorResponse.error)
374+
!('error' in errorResponse)
382375
) {
383-
throw new TypeError('Invalid error data object');
376+
throw new ErrorRPCRemote(metadata);
384377
}
385378

386379
const errorData = errorResponse.error;
@@ -389,7 +382,6 @@ function toError(errorResponse: any, metadata?: any): ErrorRPCRemote<any> {
389382
data: errorData.data === undefined ? null : errorData.data,
390383
});
391384
error.message = errorData.message;
392-
error.code = errorData.code;
393385
error.description = errorData.description;
394386
error.data = errorData.data;
395387

tests/RPC.test.ts

Lines changed: 9 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -934,8 +934,6 @@ describe('RPC', () => {
934934
sensitive: true,
935935
logger,
936936
idGen,
937-
fromError: utils.fromError,
938-
replacer: utils.replacer,
939937
});
940938
rpcServer.handleStream({ ...serverPair, cancel: () => {} });
941939

@@ -953,19 +951,20 @@ describe('RPC', () => {
953951
const errorInstance = new ErrorRPCRemote(
954952
{ code: -32006 },
955953
'Parse error',
956-
{ cause: error, data: 'The server responded with an error' },
954+
{ cause: error },
957955
);
958956

959957
const serializedError = fromError(errorInstance);
960-
const deserializedError = rpcClient.toError(serializedError);
958+
const callProm = rpcClient.methods.testMethod(serializedError);
959+
await expect(callProm).rejects.toThrow(rpcErrors.ErrorRPCRemote);
960+
961+
const deserializedError = toError(serializedError);
961962

962963
expect(deserializedError).toBeInstanceOf(ErrorRPCRemote);
963964

964965
// Check properties explicitly
965966
const { code, message, data } = deserializedError as ErrorRPCRemote<any>;
966967
expect(code).toBe(-32006);
967-
expect(message).toBe('Parse error');
968-
expect(data).toBe('The server responded with an error');
969968

970969
await rpcServer.destroy();
971970
await rpcClient.destroy();
@@ -1000,8 +999,6 @@ describe('RPC', () => {
1000999
sensitive: true,
10011000
logger,
10021001
idGen,
1003-
fromError: utils.fromError,
1004-
replacer: utils.replacer,
10051002
});
10061003
rpcServer.handleStream({ ...serverPair, cancel: () => {} });
10071004

@@ -1016,11 +1013,10 @@ describe('RPC', () => {
10161013
idGen,
10171014
});
10181015

1019-
const errorInstance = new ErrorRPCRemote(
1020-
{ code: -32006 },
1021-
'Parse error',
1022-
{ cause: error, data: 'asda' },
1023-
);
1016+
const errorInstance = new ErrorRPCRemote({ code: -32006 }, '', {
1017+
cause: error,
1018+
data: 'asda',
1019+
});
10241020

10251021
const serializedError = JSON.parse(
10261022
JSON.stringify(fromError(errorInstance), replacer('data')),
@@ -1036,7 +1032,6 @@ describe('RPC', () => {
10361032
// Check properties explicitly
10371033
const { code, message, data } = deserializedError as ErrorRPCRemote<any>;
10381034
expect(code).toBe(-32006);
1039-
expect(message).toBe('Parse error');
10401035
expect(data).toBe(undefined);
10411036

10421037
await rpcServer.destroy();

tests/RPCClient.test.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1129,7 +1129,7 @@ describe(`${RPCClient.name}`, () => {
11291129
await sleep(50);
11301130
let timeLeft = ctx.timer.getTimeout();
11311131
const message = await reader.read();
1132-
expect(ctx.timer.getTimeout()).toBeGreaterThanOrEqual(timeLeft);
1132+
expect(ctx.timer.getTimeout() + 2).toBeGreaterThanOrEqual(timeLeft);
11331133
reader.releaseLock();
11341134
for await (const _ of callerInterface.readable) {
11351135
// Do nothing
@@ -1140,7 +1140,7 @@ describe(`${RPCClient.name}`, () => {
11401140
await sleep(50);
11411141
timeLeft = ctx.timer.getTimeout();
11421142
await writer.write(message.value);
1143-
expect(ctx.timer.getTimeout()).toBeGreaterThanOrEqual(timeLeft);
1143+
expect(ctx.timer.getTimeout() + 1).toBeGreaterThanOrEqual(timeLeft);
11441144
await writer.close();
11451145

11461146
await outputResult;

tests/RPCServer.test.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -796,6 +796,7 @@ describe(`${RPCServer.name}`, () => {
796796
error: {
797797
code: 1,
798798
message: 'failure of some kind',
799+
type: 'ErrorRPCRemote',
799800
},
800801
};
801802
rpcServer.handleStream(readWriteStream);

0 commit comments

Comments
 (0)