-
Notifications
You must be signed in to change notification settings - Fork 55
/
txSubmitHttpProvider.ts
101 lines (94 loc) · 3.71 KB
/
txSubmitHttpProvider.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
/* eslint-disable @typescript-eslint/no-explicit-any */
import {
CardanoNodeUtil,
GeneralCardanoNodeError,
GeneralCardanoNodeErrorCode,
HandleOwnerChangeError,
HttpProviderConfigPaths,
ProviderError,
ProviderFailure,
TxSubmissionError,
TxSubmissionErrorCode,
TxSubmitProvider,
reasonToProviderFailure
} from '@cardano-sdk/core';
import { CreateHttpProviderConfig, createHttpProvider } from '../HttpProvider';
import { apiVersion } from '../version';
import { mapHealthCheckError } from '../mapHealthCheckError';
/** The TxSubmitProvider endpoint paths. */
const paths: HttpProviderConfigPaths<TxSubmitProvider> = {
healthCheck: '/health',
submitTx: '/submit'
};
/**
* Takes an unknown error param.
* Returns an instance of TxSubmissionError or GeneralCardanoNodeError from the error if the error
* is an object, with an undefined or valid TxSubmissionError or GeneralCardanoNodeError code, and
* a string message.
* Returns null otherwise.
*/
const toTxSubmissionError = (error: any): TxSubmissionError | GeneralCardanoNodeError | null => {
if (typeof error === 'object' && error !== null && typeof error?.message === 'string') {
if (CardanoNodeUtil.isTxSubmissionErrorCode(error.code)) {
return new TxSubmissionError(error.code, error.data, error.message);
}
if (CardanoNodeUtil.isGeneralCardanoNodeErrorCode(error.code)) {
return error instanceof GeneralCardanoNodeError
? error
: new GeneralCardanoNodeError(error.code, error.data || null, error.message);
}
if (error.code === undefined || error.code === null) {
return new GeneralCardanoNodeError(GeneralCardanoNodeErrorCode.Unknown, error?.data || null, error.message);
}
}
return null;
};
const codeToProviderFailure = (code: GeneralCardanoNodeErrorCode | TxSubmissionErrorCode) => {
switch (code) {
case GeneralCardanoNodeErrorCode.Unknown:
return ProviderFailure.Unknown;
case GeneralCardanoNodeErrorCode.ServerNotReady:
return ProviderFailure.ServerUnavailable;
default:
return ProviderFailure.BadRequest;
}
};
/**
* Connect to a Cardano Services HttpServer instance with the service available
*
* @param config The configuration object fot the TxSubmit Provider.
* @returns {TxSubmitProvider} TxSubmitProvider
* @throws {ProviderError} if reason === ProviderFailure.BadRequest then
* innerError is set to either one of CardanoNodeErrors.TxSubmissionErrors or Cardano.UnknownTxSubmissionError
*/
export const txSubmitHttpProvider = (config: CreateHttpProviderConfig<TxSubmitProvider>): TxSubmitProvider =>
createHttpProvider<TxSubmitProvider>({
...config,
apiVersion: apiVersion.txSubmit,
mapError: (error: any, method) => {
switch (method) {
case 'healthCheck': {
return mapHealthCheckError(error);
}
case 'submitTx': {
if (typeof error === 'object' && typeof error.innerError === 'object') {
// Ogmios errors have inner error. Parse that to get the real error
const txSubmissionError = toTxSubmissionError(error.innerError);
if (txSubmissionError) {
throw new ProviderError(codeToProviderFailure(txSubmissionError.code), txSubmissionError);
}
if (error.name === 'HandleOwnerChangeError') {
Object.setPrototypeOf(error, HandleOwnerChangeError);
}
}
// No inner error. Use the outer reason to determine the error type.
if (error.reason && typeof error.reason === 'string') {
throw new ProviderError(reasonToProviderFailure(error.reason), error);
}
}
}
throw new ProviderError(ProviderFailure.Unknown, error);
},
paths,
serviceSlug: 'tx-submit'
});