@lodestar/api 1.35.0-dev.f80d2d52da → 1.35.0-dev.fcf8d024ea

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (180) hide show
  1. package/lib/beacon/client/beacon.d.ts.map +1 -0
  2. package/lib/beacon/client/config.d.ts.map +1 -0
  3. package/lib/beacon/client/debug.d.ts.map +1 -0
  4. package/lib/beacon/client/events.d.ts.map +1 -0
  5. package/lib/beacon/client/index.d.ts.map +1 -0
  6. package/lib/beacon/client/index.js.map +1 -1
  7. package/lib/beacon/client/lightclient.d.ts.map +1 -0
  8. package/lib/beacon/client/lodestar.d.ts.map +1 -0
  9. package/lib/beacon/client/node.d.ts.map +1 -0
  10. package/lib/beacon/client/proof.d.ts.map +1 -0
  11. package/lib/beacon/client/validator.d.ts.map +1 -0
  12. package/lib/beacon/index.d.ts +1 -1
  13. package/lib/beacon/index.d.ts.map +1 -0
  14. package/lib/beacon/index.js.map +1 -1
  15. package/lib/beacon/routes/beacon/block.d.ts.map +1 -0
  16. package/lib/beacon/routes/beacon/index.d.ts +3 -3
  17. package/lib/beacon/routes/beacon/index.d.ts.map +1 -0
  18. package/lib/beacon/routes/beacon/index.js.map +1 -1
  19. package/lib/beacon/routes/beacon/pool.d.ts +1 -1
  20. package/lib/beacon/routes/beacon/pool.d.ts.map +1 -0
  21. package/lib/beacon/routes/beacon/rewards.d.ts.map +1 -0
  22. package/lib/beacon/routes/beacon/rewards.js.map +1 -1
  23. package/lib/beacon/routes/beacon/state.d.ts +2 -2
  24. package/lib/beacon/routes/beacon/state.d.ts.map +1 -0
  25. package/lib/beacon/routes/config.d.ts +1 -1
  26. package/lib/beacon/routes/config.d.ts.map +1 -0
  27. package/lib/beacon/routes/debug.d.ts.map +1 -0
  28. package/lib/beacon/routes/events.d.ts.map +1 -0
  29. package/lib/beacon/routes/events.js.map +1 -1
  30. package/lib/beacon/routes/index.d.ts.map +1 -0
  31. package/lib/beacon/routes/index.js.map +1 -1
  32. package/lib/beacon/routes/lightclient.d.ts.map +1 -0
  33. package/lib/beacon/routes/lodestar.d.ts.map +1 -0
  34. package/lib/beacon/routes/node.d.ts.map +1 -0
  35. package/lib/beacon/routes/proof.d.ts.map +1 -0
  36. package/lib/beacon/routes/validator.d.ts +1 -1
  37. package/lib/beacon/routes/validator.d.ts.map +1 -0
  38. package/lib/beacon/server/beacon.d.ts.map +1 -0
  39. package/lib/beacon/server/config.d.ts.map +1 -0
  40. package/lib/beacon/server/debug.d.ts.map +1 -0
  41. package/lib/beacon/server/events.d.ts.map +1 -0
  42. package/lib/beacon/server/index.d.ts +1 -1
  43. package/lib/beacon/server/index.d.ts.map +1 -0
  44. package/lib/beacon/server/index.js.map +1 -1
  45. package/lib/beacon/server/lightclient.d.ts.map +1 -0
  46. package/lib/beacon/server/lodestar.d.ts.map +1 -0
  47. package/lib/beacon/server/node.d.ts.map +1 -0
  48. package/lib/beacon/server/proof.d.ts.map +1 -0
  49. package/lib/beacon/server/validator.d.ts.map +1 -0
  50. package/lib/builder/client.d.ts.map +1 -0
  51. package/lib/builder/index.d.ts.map +1 -0
  52. package/lib/builder/index.js.map +1 -1
  53. package/lib/builder/routes.d.ts.map +1 -0
  54. package/lib/builder/routes.js.map +1 -1
  55. package/lib/builder/server/index.d.ts +1 -1
  56. package/lib/builder/server/index.d.ts.map +1 -0
  57. package/lib/index.d.ts +6 -6
  58. package/lib/index.d.ts.map +1 -0
  59. package/lib/index.js +3 -3
  60. package/lib/index.js.map +1 -1
  61. package/lib/keymanager/client.d.ts.map +1 -0
  62. package/lib/keymanager/index.d.ts +2 -2
  63. package/lib/keymanager/index.d.ts.map +1 -0
  64. package/lib/keymanager/index.js +1 -2
  65. package/lib/keymanager/index.js.map +1 -1
  66. package/lib/keymanager/routes.d.ts.map +1 -0
  67. package/lib/keymanager/server/index.d.ts +1 -1
  68. package/lib/keymanager/server/index.d.ts.map +1 -0
  69. package/lib/server/index.d.ts.map +1 -0
  70. package/lib/utils/client/error.d.ts.map +1 -0
  71. package/lib/utils/client/error.js +2 -0
  72. package/lib/utils/client/error.js.map +1 -1
  73. package/lib/utils/client/eventSource.d.ts.map +1 -0
  74. package/lib/utils/client/format.d.ts.map +1 -0
  75. package/lib/utils/client/httpClient.d.ts +1 -2
  76. package/lib/utils/client/httpClient.d.ts.map +1 -0
  77. package/lib/utils/client/httpClient.js +13 -9
  78. package/lib/utils/client/httpClient.js.map +1 -1
  79. package/lib/utils/client/index.d.ts +1 -1
  80. package/lib/utils/client/index.d.ts.map +1 -0
  81. package/lib/utils/client/index.js +1 -1
  82. package/lib/utils/client/index.js.map +1 -1
  83. package/lib/utils/client/method.d.ts.map +1 -0
  84. package/lib/utils/client/metrics.d.ts.map +1 -0
  85. package/lib/utils/client/request.d.ts.map +1 -0
  86. package/lib/utils/client/response.d.ts.map +1 -0
  87. package/lib/utils/client/response.js +6 -0
  88. package/lib/utils/client/response.js.map +1 -1
  89. package/lib/utils/codecs.d.ts.map +1 -0
  90. package/lib/utils/fork.d.ts.map +1 -0
  91. package/lib/utils/headers.d.ts.map +1 -0
  92. package/lib/utils/httpStatusCode.d.ts.map +1 -0
  93. package/lib/utils/index.d.ts.map +1 -0
  94. package/lib/utils/metadata.d.ts.map +1 -0
  95. package/lib/utils/schema.d.ts.map +1 -0
  96. package/lib/utils/serdes.d.ts.map +1 -0
  97. package/lib/utils/server/error.d.ts.map +1 -0
  98. package/lib/utils/server/error.js +1 -0
  99. package/lib/utils/server/error.js.map +1 -1
  100. package/lib/utils/server/handler.d.ts.map +1 -0
  101. package/lib/utils/server/index.d.ts.map +1 -0
  102. package/lib/utils/server/method.d.ts.map +1 -0
  103. package/lib/utils/server/parser.d.ts.map +1 -0
  104. package/lib/utils/server/route.d.ts.map +1 -0
  105. package/lib/utils/server/route.js.map +1 -1
  106. package/lib/utils/types.d.ts.map +1 -0
  107. package/lib/utils/urlFormat.d.ts.map +1 -0
  108. package/lib/utils/wireFormat.d.ts.map +1 -0
  109. package/package.json +17 -11
  110. package/src/beacon/client/beacon.ts +12 -0
  111. package/src/beacon/client/config.ts +12 -0
  112. package/src/beacon/client/debug.ts +12 -0
  113. package/src/beacon/client/events.ts +69 -0
  114. package/src/beacon/client/index.ts +46 -0
  115. package/src/beacon/client/lightclient.ts +12 -0
  116. package/src/beacon/client/lodestar.ts +12 -0
  117. package/src/beacon/client/node.ts +12 -0
  118. package/src/beacon/client/proof.ts +12 -0
  119. package/src/beacon/client/validator.ts +12 -0
  120. package/src/beacon/index.ts +24 -0
  121. package/src/beacon/routes/beacon/block.ts +602 -0
  122. package/src/beacon/routes/beacon/index.ts +66 -0
  123. package/src/beacon/routes/beacon/pool.ts +503 -0
  124. package/src/beacon/routes/beacon/rewards.ts +216 -0
  125. package/src/beacon/routes/beacon/state.ts +588 -0
  126. package/src/beacon/routes/config.ts +114 -0
  127. package/src/beacon/routes/debug.ts +231 -0
  128. package/src/beacon/routes/events.ts +337 -0
  129. package/src/beacon/routes/index.ts +33 -0
  130. package/src/beacon/routes/lightclient.ts +241 -0
  131. package/src/beacon/routes/lodestar.ts +456 -0
  132. package/src/beacon/routes/node.ts +286 -0
  133. package/src/beacon/routes/proof.ts +79 -0
  134. package/src/beacon/routes/validator.ts +1014 -0
  135. package/src/beacon/server/beacon.ts +7 -0
  136. package/src/beacon/server/config.ts +7 -0
  137. package/src/beacon/server/debug.ts +7 -0
  138. package/src/beacon/server/events.ts +73 -0
  139. package/src/beacon/server/index.ts +55 -0
  140. package/src/beacon/server/lightclient.ts +7 -0
  141. package/src/beacon/server/lodestar.ts +7 -0
  142. package/src/beacon/server/node.ts +7 -0
  143. package/src/beacon/server/proof.ts +7 -0
  144. package/src/beacon/server/validator.ts +7 -0
  145. package/src/builder/client.ts +9 -0
  146. package/src/builder/index.ts +26 -0
  147. package/src/builder/routes.ts +227 -0
  148. package/src/builder/server/index.ts +19 -0
  149. package/src/index.ts +19 -0
  150. package/src/keymanager/client.ts +9 -0
  151. package/src/keymanager/index.ts +39 -0
  152. package/src/keymanager/routes.ts +699 -0
  153. package/src/keymanager/server/index.ts +19 -0
  154. package/src/server/index.ts +2 -0
  155. package/src/utils/client/error.ts +10 -0
  156. package/src/utils/client/eventSource.ts +7 -0
  157. package/src/utils/client/format.ts +22 -0
  158. package/src/utils/client/httpClient.ts +444 -0
  159. package/src/utils/client/index.ts +6 -0
  160. package/src/utils/client/method.ts +50 -0
  161. package/src/utils/client/metrics.ts +9 -0
  162. package/src/utils/client/request.ts +113 -0
  163. package/src/utils/client/response.ts +205 -0
  164. package/src/utils/codecs.ts +143 -0
  165. package/src/utils/fork.ts +44 -0
  166. package/src/utils/headers.ts +173 -0
  167. package/src/utils/httpStatusCode.ts +392 -0
  168. package/src/utils/index.ts +3 -0
  169. package/src/utils/metadata.ts +170 -0
  170. package/src/utils/schema.ts +141 -0
  171. package/src/utils/serdes.ts +120 -0
  172. package/src/utils/server/error.ts +9 -0
  173. package/src/utils/server/handler.ts +149 -0
  174. package/src/utils/server/index.ts +5 -0
  175. package/src/utils/server/method.ts +38 -0
  176. package/src/utils/server/parser.ts +15 -0
  177. package/src/utils/server/route.ts +45 -0
  178. package/src/utils/types.ts +161 -0
  179. package/src/utils/urlFormat.ts +112 -0
  180. package/src/utils/wireFormat.ts +24 -0
@@ -0,0 +1,699 @@
1
+ import {ContainerType, ValueOf} from "@chainsafe/ssz";
2
+ import {ChainForkConfig} from "@lodestar/config";
3
+ import {Epoch, phase0, ssz, stringType} from "@lodestar/types";
4
+ import {
5
+ EmptyArgs,
6
+ EmptyMeta,
7
+ EmptyMetaCodec,
8
+ EmptyRequest,
9
+ EmptyRequestCodec,
10
+ EmptyResponseCodec,
11
+ EmptyResponseData,
12
+ JsonOnlyReq,
13
+ JsonOnlyResponseCodec,
14
+ } from "../utils/codecs.js";
15
+ import {Endpoint, RouteDefinitions, Schema} from "../utils/index.js";
16
+ import {WireFormat} from "../utils/wireFormat.js";
17
+
18
+ export enum ImportStatus {
19
+ /** Keystore successfully decrypted and imported to keymanager permanent storage */
20
+ imported = "imported",
21
+ /** Keystore's pubkey is already known to the keymanager */
22
+ duplicate = "duplicate",
23
+ /** Any other status different to the above: decrypting error, I/O errors, etc. */
24
+ error = "error",
25
+ }
26
+
27
+ export enum DeletionStatus {
28
+ /** key was active and removed */
29
+ deleted = "deleted",
30
+ /** slashing protection data returned but key was not active */
31
+ not_active = "not_active",
32
+ /** key was not found to be removed, and no slashing data can be returned */
33
+ not_found = "not_found",
34
+ /** unexpected condition meant the key could not be removed (the key was actually found, but we couldn't stop using it) - this would be a sign that making it active elsewhere would almost certainly cause you headaches / slashing conditions etc. */
35
+ error = "error",
36
+ }
37
+
38
+ export enum ImportRemoteKeyStatus {
39
+ /** Remote key successfully imported to validator client permanent storage */
40
+ imported = "imported",
41
+ /** Remote key's pubkey is already known to the validator client */
42
+ duplicate = "duplicate",
43
+ /** Any other status different to the above: I/O errors, etc. */
44
+ error = "error",
45
+ }
46
+
47
+ export enum DeleteRemoteKeyStatus {
48
+ /** key was active and removed */
49
+ deleted = "deleted",
50
+ /** key was not found to be removed */
51
+ not_found = "not_found",
52
+ /**
53
+ * unexpected condition meant the key could not be removed (the key was actually found,
54
+ * but we couldn't stop using it) - this would be a sign that making it active elsewhere would
55
+ * almost certainly cause you headaches / slashing conditions etc.
56
+ */
57
+ error = "error",
58
+ }
59
+
60
+ export type ResponseStatus<Status> = {
61
+ status: Status;
62
+ message?: string;
63
+ };
64
+
65
+ export const FeeRecipientDataType = new ContainerType(
66
+ {
67
+ pubkey: stringType,
68
+ ethaddress: stringType,
69
+ },
70
+ {jsonCase: "eth2"}
71
+ );
72
+ export const GraffitiDataType = new ContainerType(
73
+ {
74
+ pubkey: stringType,
75
+ graffiti: stringType,
76
+ },
77
+ {jsonCase: "eth2"}
78
+ );
79
+ export const GasLimitDataType = new ContainerType(
80
+ {
81
+ pubkey: stringType,
82
+ gasLimit: ssz.UintNum64,
83
+ },
84
+ {jsonCase: "eth2"}
85
+ );
86
+ export const BuilderBoostFactorDataType = new ContainerType(
87
+ {
88
+ pubkey: stringType,
89
+ builderBoostFactor: ssz.UintBn64,
90
+ },
91
+ {jsonCase: "eth2"}
92
+ );
93
+
94
+ export type FeeRecipientData = ValueOf<typeof FeeRecipientDataType>;
95
+ export type GraffitiData = ValueOf<typeof GraffitiDataType>;
96
+ export type GasLimitData = ValueOf<typeof GasLimitDataType>;
97
+ export type BuilderBoostFactorData = ValueOf<typeof BuilderBoostFactorDataType>;
98
+
99
+ export type SignerDefinition = {
100
+ pubkey: PubkeyHex;
101
+ /**
102
+ * URL to API implementing EIP-3030: BLS Remote Signer HTTP API
103
+ * `"https://remote.signer"`
104
+ */
105
+ url: string;
106
+ /** The signer associated with this pubkey cannot be deleted from the API */
107
+ readonly: boolean;
108
+ };
109
+
110
+ export type RemoteSignerDefinition = Pick<SignerDefinition, "pubkey" | "url">;
111
+
112
+ export type ProposerConfigResponse = {
113
+ graffiti?: string;
114
+ strictFeeRecipientCheck?: boolean;
115
+ feeRecipient?: string;
116
+ builder?: {
117
+ gasLimit?: number;
118
+ selection?: string;
119
+ boostFactor?: string;
120
+ };
121
+ };
122
+
123
+ /**
124
+ * JSON serialized representation of a single keystore in EIP-2335: BLS12-381 Keystore format.
125
+ * ```
126
+ * '{"version":4,"uuid":"9f75a3fa-1e5a-49f9-be3d-f5a19779c6fa","path":"m/12381/3600/0/0/0","pubkey":"0x93247f2209abcacf57b75a51dafae777f9dd38bc7053d1af526f220a7489a6d3a2753e5f3e8b1cfe39b56f43611df74a","crypto":{"kdf":{"function":"pbkdf2","params":{"dklen":32,"c":262144,"prf":"hmac-sha256","salt":"8ff8f22ef522a40f99c6ce07fdcfc1db489d54dfbc6ec35613edf5d836fa1407"},"message":""},"checksum":{"function":"sha256","params":{},"message":"9678a69833d2576e3461dd5fa80f6ac73935ae30d69d07659a709b3cd3eddbe3"},"cipher":{"function":"aes-128-ctr","params":{"iv":"31b69f0ac97261e44141b26aa0da693f"},"message":"e8228bafec4fcbaca3b827e586daad381d53339155b034e5eaae676b715ab05e"}}}'
127
+ * ```
128
+ */
129
+ export type KeystoreStr = string;
130
+
131
+ /**
132
+ * JSON serialized representation of the slash protection data in format defined in EIP-3076: Slashing Protection Interchange Format.
133
+ * ```
134
+ * '{"metadata":{"interchange_format_version":"5","genesis_validators_root":"0xcf8e0d4e9587369b2301d0790347320302cc0943d5a1884560367e8208d920f2"},"data":[{"pubkey":"0x93247f2209abcacf57b75a51dafae777f9dd38bc7053d1af526f220a7489a6d3a2753e5f3e8b1cfe39b56f43611df74a","signed_blocks":[],"signed_attestations":[]}]}'
135
+ * ```
136
+ */
137
+ export type SlashingProtectionData = string;
138
+
139
+ /**
140
+ * The validator's BLS public key, uniquely identifying them. _48-bytes, hex encoded with 0x prefix, case insensitive._
141
+ * ```
142
+ * "0x93247f2209abcacf57b75a51dafae777f9dd38bc7053d1af526f220a7489a6d3a2753e5f3e8b1cfe39b56f43611df74a"
143
+ * ```
144
+ */
145
+ export type PubkeyHex = string;
146
+
147
+ /**
148
+ * An address on the execution (Ethereum 1) network.
149
+ * ```
150
+ * "0xAbcF8e0d4e9587369b2301D0790347320302cc09"
151
+ * ```
152
+ */
153
+ export type EthAddress = string;
154
+
155
+ /**
156
+ * Arbitrary data to set in the graffiti field of BeaconBlockBody
157
+ * ```
158
+ * "plain text value"
159
+ * ```
160
+ */
161
+ export type Graffiti = string;
162
+
163
+ export type Endpoints = {
164
+ /**
165
+ * List all validating pubkeys known to and decrypted by this keymanager binary
166
+ *
167
+ * https://github.com/ethereum/keymanager-APIs/blob/0c975dae2ac6053c8245ebdb6a9f27c2f114f407/keymanager-oapi.yaml
168
+ */
169
+ listKeys: Endpoint<
170
+ "GET",
171
+ EmptyArgs,
172
+ EmptyRequest,
173
+ {
174
+ validatingPubkey: PubkeyHex;
175
+ /** The derivation path (if present in the imported keystore) */
176
+ derivationPath?: string;
177
+ /** The key associated with this pubkey cannot be deleted from the API */
178
+ readonly?: boolean;
179
+ }[],
180
+ EmptyMeta
181
+ >;
182
+
183
+ /**
184
+ * Import keystores generated by the Eth2.0 deposit CLI tooling. `passwords[i]` must unlock `keystores[i]`.
185
+ *
186
+ * Users SHOULD send slashing_protection data associated with the imported pubkeys. MUST follow the format defined in
187
+ * EIP-3076: Slashing Protection Interchange Format.
188
+ *
189
+ * Returns status result of each `request.keystores` with same length and order of `request.keystores`
190
+ *
191
+ * https://github.com/ethereum/keymanager-APIs/blob/0c975dae2ac6053c8245ebdb6a9f27c2f114f407/keymanager-oapi.yaml
192
+ */
193
+ importKeystores: Endpoint<
194
+ "POST",
195
+ {
196
+ /** JSON-encoded keystore files generated with the Launchpad */
197
+ keystores: KeystoreStr[];
198
+ /** Passwords to unlock imported keystore files. `passwords[i]` must unlock `keystores[i]` */
199
+ passwords: string[];
200
+ /** Slashing protection data for some of the keys of `keystores` */
201
+ slashingProtection?: SlashingProtectionData;
202
+ },
203
+ {body: {keystores: KeystoreStr[]; passwords: string[]; slashing_protection?: SlashingProtectionData}},
204
+ ResponseStatus<ImportStatus>[],
205
+ EmptyMeta
206
+ >;
207
+
208
+ /**
209
+ * DELETE must delete all keys from `request.pubkeys` that are known to the keymanager and exist in its
210
+ * persistent storage. Additionally, DELETE must fetch the slashing protection data for the requested keys from
211
+ * persistent storage, which must be retained (and not deleted) after the response has been sent. Therefore in the
212
+ * case of two identical delete requests being made, both will have access to slashing protection data.
213
+ *
214
+ * In a single atomic sequential operation the keymanager must:
215
+ * 1. Guarantee that key(s) can not produce any more signature; only then
216
+ * 2. Delete key(s) and serialize its associated slashing protection data
217
+ *
218
+ * DELETE should never return a 404 response, even if all pubkeys from request.pubkeys have no extant keystores
219
+ * nor slashing protection data.
220
+ *
221
+ * Slashing protection data must only be returned for keys from `request.pubkeys` for which a
222
+ * `deleted` or `not_active` status is returned.
223
+ *
224
+ * Returns deletion status of all keys in `request.pubkeys` in the same order.
225
+ *
226
+ * https://github.com/ethereum/keymanager-APIs/blob/0c975dae2ac6053c8245ebdb6a9f27c2f114f407/keymanager-oapi.yaml
227
+ */
228
+ deleteKeys: Endpoint<
229
+ "DELETE",
230
+ {
231
+ /** List of public keys to delete */
232
+ pubkeys: PubkeyHex[];
233
+ },
234
+ {body: {pubkeys: string[]}},
235
+ {statuses: ResponseStatus<DeletionStatus>[]; slashingProtection: SlashingProtectionData},
236
+ EmptyMeta
237
+ >;
238
+
239
+ /**
240
+ * List all remote validating pubkeys known to this validator client binary
241
+ */
242
+ listRemoteKeys: Endpoint<
243
+ // ⏎
244
+ "GET",
245
+ EmptyArgs,
246
+ EmptyRequest,
247
+ SignerDefinition[],
248
+ EmptyMeta
249
+ >;
250
+
251
+ /**
252
+ * Import remote keys for the validator client to request duties for
253
+ */
254
+ importRemoteKeys: Endpoint<
255
+ "POST",
256
+ {remoteSigners: RemoteSignerDefinition[]},
257
+ {body: {remote_keys: RemoteSignerDefinition[]}},
258
+ ResponseStatus<ImportRemoteKeyStatus>[],
259
+ EmptyMeta
260
+ >;
261
+
262
+ /**
263
+ * DELETE must delete all keys from `request.pubkeys` that are known to the validator client and exist in its
264
+ * persistent storage.
265
+ *
266
+ * DELETE should never return a 404 response, even if all pubkeys from `request.pubkeys` have no existing keystores.
267
+ */
268
+ deleteRemoteKeys: Endpoint<
269
+ "DELETE",
270
+ {pubkeys: PubkeyHex[]},
271
+ {body: {pubkeys: string[]}},
272
+ ResponseStatus<DeleteRemoteKeyStatus>[],
273
+ EmptyMeta
274
+ >;
275
+
276
+ listFeeRecipient: Endpoint<
277
+ // ⏎
278
+ "GET",
279
+ {pubkey: PubkeyHex},
280
+ {params: {pubkey: string}},
281
+ FeeRecipientData,
282
+ EmptyMeta
283
+ >;
284
+ setFeeRecipient: Endpoint<
285
+ "POST",
286
+ {pubkey: PubkeyHex; ethaddress: EthAddress},
287
+ {params: {pubkey: string}; body: {ethaddress: string}},
288
+ EmptyResponseData,
289
+ EmptyMeta
290
+ >;
291
+ deleteFeeRecipient: Endpoint<
292
+ // ⏎
293
+ "DELETE",
294
+ {pubkey: PubkeyHex},
295
+ {params: {pubkey: string}},
296
+ EmptyResponseData,
297
+ EmptyMeta
298
+ >;
299
+
300
+ getGraffiti: Endpoint<
301
+ // ⏎
302
+ "GET",
303
+ {pubkey: PubkeyHex},
304
+ {params: {pubkey: string}},
305
+ GraffitiData,
306
+ EmptyMeta
307
+ >;
308
+ setGraffiti: Endpoint<
309
+ "POST",
310
+ {pubkey: PubkeyHex; graffiti: Graffiti},
311
+ {params: {pubkey: string}; body: {graffiti: string}},
312
+ EmptyResponseData,
313
+ EmptyMeta
314
+ >;
315
+ deleteGraffiti: Endpoint<
316
+ // ⏎
317
+ "DELETE",
318
+ {pubkey: PubkeyHex},
319
+ {params: {pubkey: string}},
320
+ EmptyResponseData,
321
+ EmptyMeta
322
+ >;
323
+
324
+ getGasLimit: Endpoint<
325
+ // ⏎
326
+ "GET",
327
+ {pubkey: PubkeyHex},
328
+ {params: {pubkey: string}},
329
+ GasLimitData,
330
+ EmptyMeta
331
+ >;
332
+ setGasLimit: Endpoint<
333
+ "POST",
334
+ {pubkey: PubkeyHex; gasLimit: number},
335
+ {params: {pubkey: string}; body: {gas_limit: string}},
336
+ EmptyResponseData,
337
+ EmptyMeta
338
+ >;
339
+ deleteGasLimit: Endpoint<
340
+ // ⏎
341
+ "DELETE",
342
+ {pubkey: PubkeyHex},
343
+ {params: {pubkey: string}},
344
+ EmptyResponseData,
345
+ EmptyMeta
346
+ >;
347
+
348
+ getBuilderBoostFactor: Endpoint<
349
+ "GET",
350
+ {pubkey: PubkeyHex},
351
+ {params: {pubkey: string}},
352
+ BuilderBoostFactorData,
353
+ EmptyMeta
354
+ >;
355
+ setBuilderBoostFactor: Endpoint<
356
+ "POST",
357
+ {pubkey: PubkeyHex; builderBoostFactor: bigint},
358
+ {params: {pubkey: string}; body: {builder_boost_factor: string}},
359
+ EmptyResponseData,
360
+ EmptyMeta
361
+ >;
362
+ deleteBuilderBoostFactor: Endpoint<
363
+ "DELETE",
364
+ {pubkey: PubkeyHex},
365
+ {params: {pubkey: string}},
366
+ EmptyResponseData,
367
+ EmptyMeta
368
+ >;
369
+
370
+ getProposerConfig: Endpoint<
371
+ // ⏎
372
+ "GET",
373
+ {pubkey: PubkeyHex},
374
+ {params: {pubkey: string}},
375
+ ProposerConfigResponse,
376
+ EmptyMeta
377
+ >;
378
+
379
+ /**
380
+ * Create a signed voluntary exit message for an active validator, identified by a public key known to the validator
381
+ * client. This endpoint returns a `SignedVoluntaryExit` object, which can be used to initiate voluntary exit via the
382
+ * beacon node's [submitPoolVoluntaryExit](https://ethereum.github.io/beacon-APIs/#/Beacon/submitPoolVoluntaryExit) endpoint.
383
+ *
384
+ * Returns the signed voluntary exit message
385
+ *
386
+ * https://github.com/ethereum/keymanager-APIs/blob/7105e749e11dd78032ea275cc09bf62ecd548fca/keymanager-oapi.yaml
387
+ */
388
+ signVoluntaryExit: Endpoint<
389
+ "POST",
390
+ {
391
+ /** Public key of an active validator known to the validator client */
392
+ pubkey: PubkeyHex;
393
+ /** Minimum epoch for processing exit. Defaults to the current epoch if not set */
394
+ epoch?: Epoch;
395
+ },
396
+ {params: {pubkey: string}; query: {epoch?: number}},
397
+ phase0.SignedVoluntaryExit,
398
+ EmptyMeta
399
+ >;
400
+ };
401
+
402
+ export function getDefinitions(_config: ChainForkConfig): RouteDefinitions<Endpoints> {
403
+ return {
404
+ listKeys: {
405
+ url: "/eth/v1/keystores",
406
+ method: "GET",
407
+ req: EmptyRequestCodec,
408
+ resp: JsonOnlyResponseCodec,
409
+ },
410
+ importKeystores: {
411
+ url: "/eth/v1/keystores",
412
+ method: "POST",
413
+ req: JsonOnlyReq({
414
+ writeReqJson: ({keystores, passwords, slashingProtection}) => ({
415
+ body: {keystores, passwords, slashing_protection: slashingProtection},
416
+ }),
417
+ parseReqJson: ({body: {keystores, passwords, slashing_protection}}) => ({
418
+ keystores,
419
+ passwords,
420
+ slashingProtection: slashing_protection,
421
+ }),
422
+ schema: {body: Schema.Object},
423
+ }),
424
+ resp: JsonOnlyResponseCodec,
425
+ },
426
+ deleteKeys: {
427
+ url: "/eth/v1/keystores",
428
+ method: "DELETE",
429
+ req: JsonOnlyReq({
430
+ writeReqJson: ({pubkeys}) => ({body: {pubkeys}}),
431
+ parseReqJson: ({body: {pubkeys}}) => ({pubkeys}),
432
+ schema: {body: Schema.Object},
433
+ }),
434
+ resp: {
435
+ onlySupport: WireFormat.json,
436
+ data: JsonOnlyResponseCodec.data,
437
+ meta: EmptyMetaCodec,
438
+ transform: {
439
+ toResponse: (data) => {
440
+ const {statuses, slashing_protection} = data as {
441
+ statuses: ResponseStatus<DeletionStatus>[];
442
+ slashing_protection: SlashingProtectionData;
443
+ };
444
+ return {data: statuses, slashing_protection};
445
+ },
446
+ fromResponse: (resp) => {
447
+ const {data, slashing_protection} = resp as {
448
+ data: ResponseStatus<DeletionStatus>[];
449
+ slashing_protection: SlashingProtectionData;
450
+ };
451
+ return {data: {statuses: data, slashingProtection: slashing_protection}};
452
+ },
453
+ },
454
+ },
455
+ },
456
+
457
+ listRemoteKeys: {
458
+ url: "/eth/v1/remotekeys",
459
+ method: "GET",
460
+ req: EmptyRequestCodec,
461
+ resp: JsonOnlyResponseCodec,
462
+ },
463
+ importRemoteKeys: {
464
+ url: "/eth/v1/remotekeys",
465
+ method: "POST",
466
+ req: JsonOnlyReq({
467
+ writeReqJson: ({remoteSigners}) => ({body: {remote_keys: remoteSigners}}),
468
+ parseReqJson: ({body: {remote_keys}}) => ({remoteSigners: remote_keys}),
469
+ schema: {body: Schema.Object},
470
+ }),
471
+ resp: JsonOnlyResponseCodec,
472
+ },
473
+ deleteRemoteKeys: {
474
+ url: "/eth/v1/remotekeys",
475
+ method: "DELETE",
476
+ req: JsonOnlyReq({
477
+ writeReqJson: ({pubkeys}) => ({body: {pubkeys}}),
478
+ parseReqJson: ({body: {pubkeys}}) => ({pubkeys}),
479
+ schema: {body: Schema.Object},
480
+ }),
481
+ resp: JsonOnlyResponseCodec,
482
+ },
483
+
484
+ listFeeRecipient: {
485
+ url: "/eth/v1/validator/{pubkey}/feerecipient",
486
+ method: "GET",
487
+ req: {
488
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
489
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
490
+ schema: {
491
+ params: {pubkey: Schema.StringRequired},
492
+ },
493
+ },
494
+ resp: {
495
+ onlySupport: WireFormat.json,
496
+ data: FeeRecipientDataType,
497
+ meta: EmptyMetaCodec,
498
+ },
499
+ },
500
+ setFeeRecipient: {
501
+ url: "/eth/v1/validator/{pubkey}/feerecipient",
502
+ method: "POST",
503
+ req: JsonOnlyReq({
504
+ writeReqJson: ({pubkey, ethaddress}) => ({params: {pubkey}, body: {ethaddress}}),
505
+ parseReqJson: ({params: {pubkey}, body: {ethaddress}}) => ({pubkey, ethaddress}),
506
+ schema: {
507
+ params: {pubkey: Schema.StringRequired},
508
+ body: Schema.Object,
509
+ },
510
+ }),
511
+ resp: EmptyResponseCodec,
512
+ },
513
+ deleteFeeRecipient: {
514
+ url: "/eth/v1/validator/{pubkey}/feerecipient",
515
+ method: "DELETE",
516
+ req: {
517
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
518
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
519
+ schema: {
520
+ params: {pubkey: Schema.StringRequired},
521
+ },
522
+ },
523
+ resp: EmptyResponseCodec,
524
+ },
525
+
526
+ getGraffiti: {
527
+ url: "/eth/v1/validator/{pubkey}/graffiti",
528
+ method: "GET",
529
+ req: {
530
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
531
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
532
+ schema: {
533
+ params: {pubkey: Schema.StringRequired},
534
+ },
535
+ },
536
+ resp: {
537
+ onlySupport: WireFormat.json,
538
+ data: GraffitiDataType,
539
+ meta: EmptyMetaCodec,
540
+ },
541
+ },
542
+ setGraffiti: {
543
+ url: "/eth/v1/validator/{pubkey}/graffiti",
544
+ method: "POST",
545
+ req: JsonOnlyReq({
546
+ writeReqJson: ({pubkey, graffiti}) => ({params: {pubkey}, body: {graffiti}}),
547
+ parseReqJson: ({params: {pubkey}, body: {graffiti}}) => ({pubkey, graffiti}),
548
+ schema: {
549
+ params: {pubkey: Schema.StringRequired},
550
+ body: Schema.Object,
551
+ },
552
+ }),
553
+ resp: EmptyResponseCodec,
554
+ },
555
+ deleteGraffiti: {
556
+ url: "/eth/v1/validator/{pubkey}/graffiti",
557
+ method: "DELETE",
558
+ req: {
559
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
560
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
561
+ schema: {
562
+ params: {pubkey: Schema.StringRequired},
563
+ },
564
+ },
565
+ resp: EmptyResponseCodec,
566
+ },
567
+
568
+ getGasLimit: {
569
+ url: "/eth/v1/validator/{pubkey}/gas_limit",
570
+ method: "GET",
571
+ req: {
572
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
573
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
574
+ schema: {
575
+ params: {pubkey: Schema.StringRequired},
576
+ },
577
+ },
578
+ resp: {
579
+ onlySupport: WireFormat.json,
580
+ data: GasLimitDataType,
581
+ meta: EmptyMetaCodec,
582
+ },
583
+ },
584
+ setGasLimit: {
585
+ url: "/eth/v1/validator/{pubkey}/gas_limit",
586
+ method: "POST",
587
+ req: JsonOnlyReq({
588
+ writeReqJson: ({pubkey, gasLimit}) => ({params: {pubkey}, body: {gas_limit: gasLimit.toString(10)}}),
589
+ parseReqJson: ({params: {pubkey}, body: {gas_limit}}) => ({pubkey, gasLimit: parseGasLimit(gas_limit)}),
590
+ schema: {
591
+ params: {pubkey: Schema.StringRequired},
592
+ body: Schema.Object,
593
+ },
594
+ }),
595
+ resp: EmptyResponseCodec,
596
+ },
597
+ deleteGasLimit: {
598
+ url: "/eth/v1/validator/{pubkey}/gas_limit",
599
+ method: "DELETE",
600
+ req: {
601
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
602
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
603
+ schema: {
604
+ params: {pubkey: Schema.StringRequired},
605
+ },
606
+ },
607
+ resp: EmptyResponseCodec,
608
+ },
609
+
610
+ getBuilderBoostFactor: {
611
+ url: "/eth/v1/validator/{pubkey}/builder_boost_factor",
612
+ method: "GET",
613
+ req: {
614
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
615
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
616
+ schema: {
617
+ params: {pubkey: Schema.StringRequired},
618
+ },
619
+ },
620
+ resp: {
621
+ onlySupport: WireFormat.json,
622
+ data: BuilderBoostFactorDataType,
623
+ meta: EmptyMetaCodec,
624
+ },
625
+ },
626
+ setBuilderBoostFactor: {
627
+ url: "/eth/v1/validator/{pubkey}/builder_boost_factor",
628
+ method: "POST",
629
+ req: JsonOnlyReq({
630
+ writeReqJson: ({pubkey, builderBoostFactor}) => ({
631
+ params: {pubkey},
632
+ body: {builder_boost_factor: builderBoostFactor.toString(10)},
633
+ }),
634
+ parseReqJson: ({params: {pubkey}, body: {builder_boost_factor}}) => ({
635
+ pubkey,
636
+ builderBoostFactor: BigInt(builder_boost_factor),
637
+ }),
638
+ schema: {
639
+ params: {pubkey: Schema.StringRequired},
640
+ body: Schema.Object,
641
+ },
642
+ }),
643
+ resp: EmptyResponseCodec,
644
+ },
645
+ deleteBuilderBoostFactor: {
646
+ url: "/eth/v1/validator/{pubkey}/builder_boost_factor",
647
+ method: "DELETE",
648
+ req: {
649
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
650
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
651
+ schema: {
652
+ params: {pubkey: Schema.StringRequired},
653
+ },
654
+ },
655
+ resp: EmptyResponseCodec,
656
+ },
657
+
658
+ getProposerConfig: {
659
+ url: "/eth/v0/validator/{pubkey}/proposer_config",
660
+ method: "GET",
661
+ req: {
662
+ writeReq: ({pubkey}) => ({params: {pubkey}}),
663
+ parseReq: ({params: {pubkey}}) => ({pubkey}),
664
+ schema: {
665
+ params: {pubkey: Schema.StringRequired},
666
+ },
667
+ },
668
+ resp: JsonOnlyResponseCodec,
669
+ },
670
+
671
+ signVoluntaryExit: {
672
+ url: "/eth/v1/validator/{pubkey}/voluntary_exit",
673
+ method: "POST",
674
+ req: {
675
+ writeReq: ({pubkey, epoch}) => ({params: {pubkey}, query: {epoch}}),
676
+ parseReq: ({params: {pubkey}, query: {epoch}}) => ({pubkey, epoch}),
677
+ schema: {
678
+ params: {pubkey: Schema.StringRequired},
679
+ query: {epoch: Schema.Uint},
680
+ },
681
+ },
682
+ resp: {
683
+ data: ssz.phase0.SignedVoluntaryExit,
684
+ meta: EmptyMetaCodec,
685
+ },
686
+ },
687
+ };
688
+ }
689
+
690
+ function parseGasLimit(gasLimitInput: string | number): number {
691
+ if ((typeof gasLimitInput !== "string" && typeof gasLimitInput !== "number") || `${gasLimitInput}`.trim() === "") {
692
+ throw Error("Not valid Gas Limit");
693
+ }
694
+ const gasLimit = Number(gasLimitInput);
695
+ if (Number.isNaN(gasLimit) || gasLimit === 0) {
696
+ throw Error(`Gas Limit is not valid gasLimit=${gasLimit}`);
697
+ }
698
+ return gasLimit;
699
+ }