@solana/web3.js 1.78.0 → 2.0.0-development
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.
- package/README.md +56 -112
- package/dist/index.browser.cjs +158 -0
- package/dist/index.browser.cjs.map +1 -0
- package/dist/index.browser.js +137 -0
- package/dist/index.browser.js.map +1 -0
- package/dist/index.development.js +1044 -0
- package/dist/index.development.js.map +1 -0
- package/dist/index.native.js +139 -0
- package/dist/index.native.js.map +1 -0
- package/dist/index.node.cjs +158 -0
- package/dist/index.node.cjs.map +1 -0
- package/dist/index.node.js +139 -0
- package/dist/index.node.js.map +1 -0
- package/dist/index.production.min.js +25 -0
- package/dist/types/index.d.ts +5 -0
- package/dist/types/rpc-default-config.d.ts +3 -0
- package/dist/types/rpc-integer-overflow-error.d.ts +8 -0
- package/dist/types/rpc-request-coalescer.d.ts +5 -0
- package/dist/types/rpc-request-deduplication.d.ts +2 -0
- package/dist/types/rpc-transport.d.ts +4 -0
- package/dist/types/rpc.d.ts +5 -0
- package/package.json +86 -111
- package/lib/index.browser.cjs.js +0 -10248
- package/lib/index.browser.cjs.js.map +0 -1
- package/lib/index.browser.esm.js +0 -10145
- package/lib/index.browser.esm.js.map +0 -1
- package/lib/index.cjs.js +0 -12748
- package/lib/index.cjs.js.map +0 -1
- package/lib/index.d.ts +0 -3904
- package/lib/index.esm.js +0 -12638
- package/lib/index.esm.js.map +0 -1
- package/lib/index.iife.js +0 -26757
- package/lib/index.iife.js.map +0 -1
- package/lib/index.iife.min.js +0 -20
- package/lib/index.iife.min.js.map +0 -1
- package/lib/index.native.js +0 -10248
- package/lib/index.native.js.map +0 -1
- package/src/__forks__/browser/fetch-impl.ts +0 -4
- package/src/__forks__/browser/rpc-websocket-factory.ts +0 -1
- package/src/__forks__/react-native/fetch-impl.ts +0 -4
- package/src/__forks__/react-native/rpc-websocket-factory.ts +0 -1
- package/src/account-data.ts +0 -39
- package/src/account.ts +0 -55
- package/src/blockhash.ts +0 -4
- package/src/bpf-loader-deprecated.ts +0 -5
- package/src/bpf-loader.ts +0 -45
- package/src/connection.ts +0 -6796
- package/src/epoch-schedule.ts +0 -102
- package/src/errors.ts +0 -50
- package/src/fee-calculator.ts +0 -18
- package/src/fetch-impl.ts +0 -13
- package/src/index.ts +0 -24
- package/src/instruction.ts +0 -58
- package/src/keypair.ts +0 -93
- package/src/layout.ts +0 -188
- package/src/loader.ts +0 -267
- package/src/message/account-keys.ts +0 -79
- package/src/message/compiled-keys.ts +0 -165
- package/src/message/index.ts +0 -47
- package/src/message/legacy.ts +0 -326
- package/src/message/v0.ts +0 -496
- package/src/message/versioned.ts +0 -36
- package/src/nonce-account.ts +0 -82
- package/src/programs/address-lookup-table/index.ts +0 -435
- package/src/programs/address-lookup-table/state.ts +0 -84
- package/src/programs/compute-budget.ts +0 -281
- package/src/programs/ed25519.ts +0 -157
- package/src/programs/index.ts +0 -7
- package/src/programs/secp256k1.ts +0 -228
- package/src/programs/stake.ts +0 -935
- package/src/programs/system.ts +0 -1048
- package/src/programs/vote.ts +0 -543
- package/src/publickey.ts +0 -259
- package/src/rpc-websocket-factory.ts +0 -4
- package/src/rpc-websocket.ts +0 -79
- package/src/sysvar.ts +0 -37
- package/src/timing.ts +0 -23
- package/src/transaction/constants.ts +0 -12
- package/src/transaction/expiry-custom-errors.ts +0 -48
- package/src/transaction/index.ts +0 -5
- package/src/transaction/legacy.ts +0 -918
- package/src/transaction/message.ts +0 -140
- package/src/transaction/versioned.ts +0 -126
- package/src/utils/assert.ts +0 -8
- package/src/utils/bigint.ts +0 -43
- package/src/utils/borsh-schema.ts +0 -38
- package/src/utils/cluster.ts +0 -31
- package/src/utils/ed25519.ts +0 -43
- package/src/utils/index.ts +0 -5
- package/src/utils/makeWebsocketUrl.ts +0 -26
- package/src/utils/promise-timeout.ts +0 -14
- package/src/utils/secp256k1.ts +0 -11
- package/src/utils/send-and-confirm-raw-transaction.ts +0 -102
- package/src/utils/send-and-confirm-transaction.ts +0 -98
- package/src/utils/shortvec-encoding.ts +0 -28
- package/src/utils/sleep.ts +0 -4
- package/src/utils/to-buffer.ts +0 -11
- package/src/validator-info.ts +0 -104
- package/src/vote-account.ts +0 -236
package/README.md
CHANGED
|
@@ -6,150 +6,94 @@
|
|
|
6
6
|
|
|
7
7
|
[code-style-prettier-image]: https://img.shields.io/badge/code_style-prettier-ff69b4.svg?style=flat-square
|
|
8
8
|
[code-style-prettier-url]: https://github.com/prettier/prettier
|
|
9
|
-
[npm-downloads-image]: https://img.shields.io/npm/dm/@solana/web3.js.svg?style=flat
|
|
10
|
-
[npm-image]: https://img.shields.io/npm/v/@solana/web3.js.svg?style=flat
|
|
11
|
-
[npm-url]: https://www.npmjs.com/package/@solana/web3.js
|
|
9
|
+
[npm-downloads-image]: https://img.shields.io/npm/dm/@solana/web3.js/experimental.svg?style=flat
|
|
10
|
+
[npm-image]: https://img.shields.io/npm/v/@solana/web3.js/experimental.svg?style=flat
|
|
11
|
+
[npm-url]: https://www.npmjs.com/package/@solana/web3.js/v/experimental
|
|
12
12
|
[semantic-release-image]: https://img.shields.io/badge/%20%20%F0%9F%93%A6%F0%9F%9A%80-semantic--release-e10079.svg
|
|
13
13
|
[semantic-release-url]: https://github.com/semantic-release/semantic-release
|
|
14
14
|
|
|
15
|
-
# Solana JavaScript SDK
|
|
15
|
+
# Experimental Solana JavaScript SDK
|
|
16
16
|
|
|
17
|
-
Use this to interact with accounts and programs on the Solana network through the Solana [JSON
|
|
17
|
+
Use this to interact with accounts and programs on the Solana network through the Solana [JSON-RPC API](https://docs.solana.com/apps/jsonrpc-api).
|
|
18
|
+
|
|
19
|
+
**This library is experimental**. It is unsuitable for production use, because the API is unstable and may change without warning. If you want to build a production Solana application, use the [1.x branch](https://www.npmjs.com/package/@solana/web3.js).
|
|
18
20
|
|
|
19
21
|
## Installation
|
|
20
22
|
|
|
21
|
-
### For use in Node.js or a web application
|
|
23
|
+
### For use in Node.js, React Native, or a web application
|
|
22
24
|
|
|
23
|
-
```
|
|
24
|
-
|
|
25
|
+
```shell
|
|
26
|
+
npm install --save @solana/web3.js@experimental
|
|
25
27
|
```
|
|
26
28
|
|
|
27
29
|
### For use in a browser, without a build system
|
|
28
30
|
|
|
29
31
|
```html
|
|
30
|
-
<!-- Development (
|
|
31
|
-
<script src="https://unpkg.com/@solana/web3.js@
|
|
32
|
+
<!-- Development (debug mode, unminified) -->
|
|
33
|
+
<script src="https://unpkg.com/@solana/web3.js@experimental/dist/index.development.js"></script>
|
|
32
34
|
|
|
33
35
|
<!-- Production (minified) -->
|
|
34
|
-
<script src="https://unpkg.com/@solana/web3.js@
|
|
36
|
+
<script src="https://unpkg.com/@solana/web3.js@experimental/dist/index.production.min.js"></script>
|
|
35
37
|
```
|
|
36
38
|
|
|
37
|
-
##
|
|
38
|
-
|
|
39
|
-
- [The Solana Cookbook](https://solanacookbook.com/) has extensive task-based documentation using this library.
|
|
40
|
-
- For more detail on individual functions, see the [latest API Documentation](https://solana-labs.github.io/solana-web3.js)
|
|
39
|
+
## Usage
|
|
41
40
|
|
|
42
|
-
|
|
41
|
+
There are 3 main applications of this library.
|
|
43
42
|
|
|
44
|
-
|
|
43
|
+
1. **RPC**. Solana apps interact with the network by calling methods on the Solana JSON-RPC.
|
|
44
|
+
2. **Transactions**. Solana apps interact with Solana program by building and sending transactions.
|
|
45
|
+
3. **Keys**. People use cryptographic keys to verify the provenance of messages and to attest to the ownership of their accounts.
|
|
45
46
|
|
|
46
|
-
|
|
47
|
+
### RPC
|
|
47
48
|
|
|
48
|
-
|
|
49
|
-
- Source code, if possible
|
|
50
|
-
- The text of any errors you encountered, with stacktraces if available
|
|
49
|
+
First, configure your connection to an RPC server. This might be a server that you host, one that you lease, or one of the limited-use [public RPC servers](https://docs.solana.com/cluster/rpc-endpoints).
|
|
51
50
|
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
51
|
+
```ts
|
|
52
|
+
import { createDefaultRpcTransport } from '@solana/web3.js';
|
|
53
|
+
const devnetTransport = createDefaultRpcTransport({ url: 'https://api.devnet.solana.com' });
|
|
54
|
+
```
|
|
55
55
|
|
|
56
|
-
|
|
57
|
-
- Chrome: May 2018
|
|
58
|
-
- Firefox: July 2019
|
|
59
|
-
- Safari: September 2020
|
|
60
|
-
- Mobile Safari: September 2020
|
|
61
|
-
- Edge: January 2020
|
|
62
|
-
- Opera: June 2018
|
|
63
|
-
- Samsung Internet: April 2019
|
|
64
|
-
- Runtimes, [by version](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/BigInt):
|
|
65
|
-
- Deno: >=1.0
|
|
66
|
-
- Node: >=10.4.0
|
|
67
|
-
- React Native:
|
|
68
|
-
- \>=0.7.0 using the [Hermes](https://reactnative.dev/blog/2022/07/08/hermes-as-the-default) engine ([integration guide](https://solanacookbook.com/integrations/react-native.html#how-to-use-solana-web3-js-in-a-react-native-app)):
|
|
56
|
+
Second, construct an RPC instance that uses that transport.
|
|
69
57
|
|
|
70
|
-
|
|
58
|
+
```ts
|
|
59
|
+
const devnetRpc = createSolanaRpc({ transport: devnetTransport });
|
|
60
|
+
```
|
|
71
61
|
|
|
72
|
-
|
|
62
|
+
Now, you can use it to call methods on your RPC server. For instance, here is how you would fetch an account's balance.
|
|
73
63
|
|
|
74
|
-
|
|
64
|
+
```ts
|
|
65
|
+
const systemProgramAddress = '11111111111111111111111111111111' as Base58EncodedAddress;
|
|
66
|
+
const balanceInLamports = await devnetRpc.getBalance(systemProgramAddress).send();
|
|
67
|
+
console.log('Balance of System Program account in Lamports', balanceInLamports);
|
|
68
|
+
```
|
|
75
69
|
|
|
76
|
-
|
|
70
|
+
### Transactions
|
|
77
71
|
|
|
78
|
-
|
|
79
|
-
$ npm test
|
|
80
|
-
```
|
|
72
|
+
Unimplemented.
|
|
81
73
|
|
|
82
|
-
|
|
74
|
+
### Keys
|
|
83
75
|
|
|
84
|
-
|
|
76
|
+
#### Addresses and public keys
|
|
85
77
|
|
|
86
|
-
|
|
78
|
+
Client applications primarily deal with addresses and public keys in the form of base58-encoded strings. Addresses and public keys returned from the RPC API conform to the type `Base58EncodedAddress`. You can use a value of that type wherever a base58-encoded address or key is expected.
|
|
87
79
|
|
|
88
|
-
|
|
89
|
-
$ npm run test:live-with-test-validator:setup
|
|
90
|
-
```
|
|
80
|
+
From time to time you might acquire a string, that you expect to validate as an address, from an untrusted network API or user input. To assert that such an arbitrary string is a base58-encoded address, use the `assertIsBase58EncodedAddress` function.
|
|
91
81
|
|
|
92
|
-
|
|
82
|
+
```ts
|
|
83
|
+
import { assertIsBase58EncodedAddress } from '@solana/web3.js`;
|
|
93
84
|
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
85
|
+
// Imagine a function that fetches an account's balance when a user submits a form.
|
|
86
|
+
function handleSubmit() {
|
|
87
|
+
// We know only that what the user typed conforms to the `string` type.
|
|
88
|
+
const address: string = accountAddressInput.value;
|
|
89
|
+
try {
|
|
90
|
+
// If this type assertion function doesn't throw, then
|
|
91
|
+
// Typescript will upcast `address` to `Base58EncodedAddress`.
|
|
92
|
+
assertIsBase58EncodedAddress(address);
|
|
93
|
+
// At this point, `address` is a `Base58EncodedAddress` that can be used with the RPC.
|
|
94
|
+
const balanceInLamports = await rpc.getBalance(address).send();
|
|
95
|
+
} catch (e) {
|
|
96
|
+
// `address` turned out not to be a base58-encoded address
|
|
97
|
+
}
|
|
98
|
+
}
|
|
97
99
|
```
|
|
98
|
-
|
|
99
|
-
### Speed up build times with remote caching
|
|
100
|
-
|
|
101
|
-
Cache build artifacts remotely so that you, others, and the CI server can take advantage of each others' build efforts.
|
|
102
|
-
|
|
103
|
-
1. Log the Turborepo CLI into the Solana Vercel account
|
|
104
|
-
```shell
|
|
105
|
-
pnpm turbo login
|
|
106
|
-
```
|
|
107
|
-
2. Link the repository to the remote cache
|
|
108
|
-
```shell
|
|
109
|
-
pnpm turbo link
|
|
110
|
-
```
|
|
111
|
-
|
|
112
|
-
## Contributing
|
|
113
|
-
|
|
114
|
-
If you found a bug or would like to request a feature, please [file an issue](https://github.com/solana-labs/solana-web3.js/issues/new). If, based on the discussion on an issue you would like to offer a code change, please make a [pull request](https://github.com/solana-labs/solana-web3.js/compare). If neither of these describes what you would like to contribute, read the [getting help](#getting-help) section above.
|
|
115
|
-
|
|
116
|
-
## Disclaimer
|
|
117
|
-
|
|
118
|
-
All claims, content, designs, algorithms, estimates, roadmaps,
|
|
119
|
-
specifications, and performance measurements described in this project
|
|
120
|
-
are done with the Solana Foundation's ("SF") best efforts. It is up to
|
|
121
|
-
the reader to check and validate their accuracy and truthfulness.
|
|
122
|
-
Furthermore nothing in this project constitutes a solicitation for
|
|
123
|
-
investment.
|
|
124
|
-
|
|
125
|
-
Any content produced by SF or developer resources that SF provides, are
|
|
126
|
-
for educational and inspiration purposes only. SF does not encourage,
|
|
127
|
-
induce or sanction the deployment, integration or use of any such
|
|
128
|
-
applications (including the code comprising the Solana blockchain
|
|
129
|
-
protocol) in violation of applicable laws or regulations and hereby
|
|
130
|
-
prohibits any such deployment, integration or use. This includes use of
|
|
131
|
-
any such applications by the reader (a) in violation of export control
|
|
132
|
-
or sanctions laws of the United States or any other applicable
|
|
133
|
-
jurisdiction, (b) if the reader is located in or ordinarily resident in
|
|
134
|
-
a country or territory subject to comprehensive sanctions administered
|
|
135
|
-
by the U.S. Office of Foreign Assets Control (OFAC), or (c) if the
|
|
136
|
-
reader is or is working on behalf of a Specially Designated National
|
|
137
|
-
(SDN) or a person subject to similar blocking or denied party
|
|
138
|
-
prohibitions.
|
|
139
|
-
|
|
140
|
-
The reader should be aware that U.S. export control and sanctions laws
|
|
141
|
-
prohibit U.S. persons (and other persons that are subject to such laws)
|
|
142
|
-
from transacting with persons in certain countries and territories or
|
|
143
|
-
that are on the SDN list. As a project based primarily on open-source
|
|
144
|
-
software, it is possible that such sanctioned persons may nevertheless
|
|
145
|
-
bypass prohibitions, obtain the code comprising the Solana blockchain
|
|
146
|
-
protocol (or other project code or applications) and deploy, integrate,
|
|
147
|
-
or otherwise use it. Accordingly, there is a risk to individuals that
|
|
148
|
-
other persons using the Solana blockchain protocol may be sanctioned
|
|
149
|
-
persons and that transactions with such persons would be a violation of
|
|
150
|
-
U.S. export controls and sanctions law. This risk applies to
|
|
151
|
-
individuals, organizations, and other ecosystem participants that
|
|
152
|
-
deploy, integrate, or use the Solana blockchain protocol code directly
|
|
153
|
-
(e.g., as a node operator), and individuals that transact on the Solana
|
|
154
|
-
blockchain through light clients, third party interfaces, and/or wallet
|
|
155
|
-
software.
|
|
@@ -0,0 +1,158 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var instructions = require('@solana/instructions');
|
|
4
|
+
var keys = require('@solana/keys');
|
|
5
|
+
var rpcCore = require('@solana/rpc-core');
|
|
6
|
+
var rpcTransport = require('@solana/rpc-transport');
|
|
7
|
+
var fastStableStringify = require('fast-stable-stringify');
|
|
8
|
+
|
|
9
|
+
function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
|
|
10
|
+
|
|
11
|
+
var fastStableStringify__default = /*#__PURE__*/_interopDefault(fastStableStringify);
|
|
12
|
+
|
|
13
|
+
// src/index.ts
|
|
14
|
+
|
|
15
|
+
// src/rpc-integer-overflow-error.ts
|
|
16
|
+
var SolanaJsonRpcIntegerOverflowError = class extends Error {
|
|
17
|
+
constructor(methodName, keyPath, value) {
|
|
18
|
+
const argPosition = (typeof keyPath[0] === "number" ? keyPath[0] : parseInt(keyPath[0], 10)) + 1;
|
|
19
|
+
let ordinal = "";
|
|
20
|
+
const lastDigit = argPosition % 10;
|
|
21
|
+
const lastTwoDigits = argPosition % 100;
|
|
22
|
+
if (lastDigit == 1 && lastTwoDigits != 11) {
|
|
23
|
+
ordinal = argPosition + "st";
|
|
24
|
+
} else if (lastDigit == 2 && lastTwoDigits != 12) {
|
|
25
|
+
ordinal = argPosition + "nd";
|
|
26
|
+
} else if (lastDigit == 3 && lastTwoDigits != 13) {
|
|
27
|
+
ordinal = argPosition + "rd";
|
|
28
|
+
} else {
|
|
29
|
+
ordinal = argPosition + "th";
|
|
30
|
+
}
|
|
31
|
+
const path = keyPath.length > 1 ? keyPath.slice(1).map((pathPart) => typeof pathPart === "number" ? `[${pathPart}]` : pathPart).join(".") : null;
|
|
32
|
+
super(
|
|
33
|
+
`The ${ordinal} argument to the \`${methodName}\` RPC method${path ? ` at path \`${path}\`` : ""} was \`${value}\`. This number is unsafe for use with the Solana JSON-RPC because it exceeds \`Number.MAX_SAFE_INTEGER\`.`
|
|
34
|
+
);
|
|
35
|
+
this.keyPath = keyPath;
|
|
36
|
+
this.methodName = methodName;
|
|
37
|
+
this.value = value;
|
|
38
|
+
}
|
|
39
|
+
get name() {
|
|
40
|
+
return "SolanaJsonRpcIntegerOverflowError";
|
|
41
|
+
}
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
// src/rpc-default-config.ts
|
|
45
|
+
var DEFAULT_RPC_CONFIG = {
|
|
46
|
+
onIntegerOverflow(methodName, keyPath, value) {
|
|
47
|
+
throw new SolanaJsonRpcIntegerOverflowError(methodName, keyPath, value);
|
|
48
|
+
}
|
|
49
|
+
};
|
|
50
|
+
|
|
51
|
+
// src/rpc.ts
|
|
52
|
+
function createSolanaRpc(config) {
|
|
53
|
+
return rpcTransport.createJsonRpc({
|
|
54
|
+
...config,
|
|
55
|
+
api: rpcCore.createSolanaRpcApi(DEFAULT_RPC_CONFIG)
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
// src/rpc-request-coalescer.ts
|
|
60
|
+
function getRpcTransportWithRequestCoalescing(transport, getDeduplicationKey) {
|
|
61
|
+
let coalescedRequestsByDeduplicationKey;
|
|
62
|
+
return async function makeCoalescedHttpRequest(config) {
|
|
63
|
+
const { payload, signal } = config;
|
|
64
|
+
const deduplicationKey = getDeduplicationKey(payload);
|
|
65
|
+
if (deduplicationKey === void 0) {
|
|
66
|
+
return await transport(config);
|
|
67
|
+
}
|
|
68
|
+
if (!coalescedRequestsByDeduplicationKey) {
|
|
69
|
+
Promise.resolve().then(() => {
|
|
70
|
+
coalescedRequestsByDeduplicationKey = void 0;
|
|
71
|
+
});
|
|
72
|
+
coalescedRequestsByDeduplicationKey = {};
|
|
73
|
+
}
|
|
74
|
+
if (coalescedRequestsByDeduplicationKey[deduplicationKey] == null) {
|
|
75
|
+
const abortController = new AbortController();
|
|
76
|
+
coalescedRequestsByDeduplicationKey[deduplicationKey] = {
|
|
77
|
+
abortController,
|
|
78
|
+
numConsumers: 0,
|
|
79
|
+
responsePromise: transport({
|
|
80
|
+
...config,
|
|
81
|
+
signal: abortController.signal
|
|
82
|
+
})
|
|
83
|
+
};
|
|
84
|
+
}
|
|
85
|
+
const coalescedRequest = coalescedRequestsByDeduplicationKey[deduplicationKey];
|
|
86
|
+
coalescedRequest.numConsumers++;
|
|
87
|
+
if (signal) {
|
|
88
|
+
const responsePromise = coalescedRequest.responsePromise;
|
|
89
|
+
return await new Promise((resolve, reject) => {
|
|
90
|
+
const handleAbort = (e) => {
|
|
91
|
+
signal.removeEventListener("abort", handleAbort);
|
|
92
|
+
coalescedRequest.numConsumers -= 1;
|
|
93
|
+
if (coalescedRequest.numConsumers === 0) {
|
|
94
|
+
const abortController = coalescedRequest.abortController;
|
|
95
|
+
abortController.abort();
|
|
96
|
+
}
|
|
97
|
+
const abortError = new DOMException(e.target.reason, "AbortError");
|
|
98
|
+
reject(abortError);
|
|
99
|
+
};
|
|
100
|
+
signal.addEventListener("abort", handleAbort);
|
|
101
|
+
responsePromise.then(resolve).finally(() => {
|
|
102
|
+
signal.removeEventListener("abort", handleAbort);
|
|
103
|
+
});
|
|
104
|
+
});
|
|
105
|
+
} else {
|
|
106
|
+
return await coalescedRequest.responsePromise;
|
|
107
|
+
}
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
function getSolanaRpcPayloadDeduplicationKey(payload) {
|
|
111
|
+
if (payload == null || typeof payload !== "object" || Array.isArray(payload)) {
|
|
112
|
+
return;
|
|
113
|
+
}
|
|
114
|
+
if ("jsonrpc" in payload && payload.jsonrpc === "2.0" && "method" in payload && "params" in payload) {
|
|
115
|
+
return fastStableStringify__default.default([payload.method, payload.params]);
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
// src/rpc-transport.ts
|
|
120
|
+
function normalizeHeaders(headers) {
|
|
121
|
+
const out = {};
|
|
122
|
+
for (const headerName in headers) {
|
|
123
|
+
out[headerName.toLowerCase()] = headers[headerName];
|
|
124
|
+
}
|
|
125
|
+
return out;
|
|
126
|
+
}
|
|
127
|
+
function createDefaultRpcTransport(config) {
|
|
128
|
+
return getRpcTransportWithRequestCoalescing(
|
|
129
|
+
rpcTransport.createHttpTransport({
|
|
130
|
+
...config,
|
|
131
|
+
headers: {
|
|
132
|
+
...config.headers ? normalizeHeaders(config.headers) : void 0,
|
|
133
|
+
...{
|
|
134
|
+
// Keep these headers lowercase so they will override any user-supplied headers above.
|
|
135
|
+
"solana-client": `js/${"2.0.0-development"}` ?? "UNKNOWN"
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
}),
|
|
139
|
+
getSolanaRpcPayloadDeduplicationKey
|
|
140
|
+
);
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
exports.createDefaultRpcTransport = createDefaultRpcTransport;
|
|
144
|
+
exports.createSolanaRpc = createSolanaRpc;
|
|
145
|
+
Object.keys(instructions).forEach(function (k) {
|
|
146
|
+
if (k !== 'default' && !exports.hasOwnProperty(k)) Object.defineProperty(exports, k, {
|
|
147
|
+
enumerable: true,
|
|
148
|
+
get: function () { return instructions[k]; }
|
|
149
|
+
});
|
|
150
|
+
});
|
|
151
|
+
Object.keys(keys).forEach(function (k) {
|
|
152
|
+
if (k !== 'default' && !exports.hasOwnProperty(k)) Object.defineProperty(exports, k, {
|
|
153
|
+
enumerable: true,
|
|
154
|
+
get: function () { return keys[k]; }
|
|
155
|
+
});
|
|
156
|
+
});
|
|
157
|
+
//# sourceMappingURL=out.js.map
|
|
158
|
+
//# sourceMappingURL=index.browser.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/rpc.ts","../src/rpc-integer-overflow-error.ts","../src/rpc-default-config.ts","../src/rpc-transport.ts","../src/rpc-request-coalescer.ts","../src/rpc-request-deduplication.ts"],"names":[],"mappings":"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","sourcesContent":["export * from '@solana/instructions';\nexport * from '@solana/keys';\nexport * from './rpc';\nexport * from './rpc-transport';\n","import { createSolanaRpcApi, SolanaRpcMethods } from '@solana/rpc-core';\nimport { createJsonRpc } from '@solana/rpc-transport';\nimport type { Rpc } from '@solana/rpc-transport/dist/types/json-rpc-types';\n\nimport { DEFAULT_RPC_CONFIG } from './rpc-default-config';\n\nexport function createSolanaRpc(config: Omit<Parameters<typeof createJsonRpc>[0], 'api'>): Rpc<SolanaRpcMethods> {\n return createJsonRpc<SolanaRpcMethods>({\n ...config,\n api: createSolanaRpcApi(DEFAULT_RPC_CONFIG),\n });\n}\n","export class SolanaJsonRpcIntegerOverflowError extends Error {\n readonly methodName: string;\n readonly keyPath: (number | string)[];\n readonly value: bigint;\n constructor(methodName: string, keyPath: (number | string)[], value: bigint) {\n const argPosition = (typeof keyPath[0] === 'number' ? keyPath[0] : parseInt(keyPath[0], 10)) + 1;\n let ordinal = '';\n const lastDigit = argPosition % 10;\n const lastTwoDigits = argPosition % 100;\n if (lastDigit == 1 && lastTwoDigits != 11) {\n ordinal = argPosition + 'st';\n } else if (lastDigit == 2 && lastTwoDigits != 12) {\n ordinal = argPosition + 'nd';\n } else if (lastDigit == 3 && lastTwoDigits != 13) {\n ordinal = argPosition + 'rd';\n } else {\n ordinal = argPosition + 'th';\n }\n const path =\n keyPath.length > 1\n ? keyPath\n .slice(1)\n .map(pathPart => (typeof pathPart === 'number' ? `[${pathPart}]` : pathPart))\n .join('.')\n : null;\n super(\n `The ${ordinal} argument to the \\`${methodName}\\` RPC method` +\n `${path ? ` at path \\`${path}\\`` : ''} was \\`${value}\\`. This number is ` +\n 'unsafe for use with the Solana JSON-RPC because it exceeds ' +\n '`Number.MAX_SAFE_INTEGER`.'\n );\n this.keyPath = keyPath;\n this.methodName = methodName;\n this.value = value;\n }\n get name() {\n return 'SolanaJsonRpcIntegerOverflowError';\n }\n}\n","import { createSolanaRpcApi } from '@solana/rpc-core';\n\nimport { SolanaJsonRpcIntegerOverflowError } from './rpc-integer-overflow-error';\n\nexport const DEFAULT_RPC_CONFIG: Partial<Parameters<typeof createSolanaRpcApi>[0]> = {\n onIntegerOverflow(methodName, keyPath, value) {\n throw new SolanaJsonRpcIntegerOverflowError(methodName, keyPath, value);\n },\n};\n","import { createHttpTransport } from '@solana/rpc-transport';\nimport { IRpcTransport } from '@solana/rpc-transport/dist/types/transports/transport-types';\n\nimport { getRpcTransportWithRequestCoalescing } from './rpc-request-coalescer';\nimport { getSolanaRpcPayloadDeduplicationKey } from './rpc-request-deduplication';\n\n/**\n * Lowercasing header names makes it easier to override user-supplied headers.\n */\nfunction normalizeHeaders<T extends Record<string, string>>(\n headers: T\n): { [K in keyof T & string as Lowercase<K>]: T[K] } {\n const out: Record<string, string> = {};\n for (const headerName in headers) {\n out[headerName.toLowerCase()] = headers[headerName];\n }\n return out as { [K in keyof T & string as Lowercase<K>]: T[K] };\n}\n\nexport function createDefaultRpcTransport(config: Parameters<typeof createHttpTransport>[0]): IRpcTransport {\n return getRpcTransportWithRequestCoalescing(\n createHttpTransport({\n ...config,\n headers: {\n ...(config.headers ? normalizeHeaders(config.headers) : undefined),\n ...({\n // Keep these headers lowercase so they will override any user-supplied headers above.\n 'solana-client': `js/${__VERSION__}` ?? 'UNKNOWN',\n } as { [overrideHeader: string]: string }),\n },\n }),\n getSolanaRpcPayloadDeduplicationKey\n );\n}\n","import { IRpcTransport } from '@solana/rpc-transport/dist/types/transports/transport-types';\n\ntype CoalescedRequest = {\n readonly abortController: AbortController;\n numConsumers: number;\n readonly responsePromise: Promise<unknown>;\n};\n\ntype GetDeduplicationKeyFn = (payload: unknown) => string | undefined;\n\nexport function getRpcTransportWithRequestCoalescing(\n transport: IRpcTransport,\n getDeduplicationKey: GetDeduplicationKeyFn\n): IRpcTransport {\n let coalescedRequestsByDeduplicationKey: Record<string, CoalescedRequest> | undefined;\n return async function makeCoalescedHttpRequest<TResponse>(\n config: Parameters<IRpcTransport>[0]\n ): Promise<TResponse> {\n const { payload, signal } = config;\n const deduplicationKey = getDeduplicationKey(payload);\n if (deduplicationKey === undefined) {\n return await transport(config);\n }\n if (!coalescedRequestsByDeduplicationKey) {\n Promise.resolve().then(() => {\n coalescedRequestsByDeduplicationKey = undefined;\n });\n coalescedRequestsByDeduplicationKey = {};\n }\n if (coalescedRequestsByDeduplicationKey[deduplicationKey] == null) {\n const abortController = new AbortController();\n coalescedRequestsByDeduplicationKey[deduplicationKey] = {\n abortController,\n numConsumers: 0,\n responsePromise: transport<TResponse>({\n ...config,\n signal: abortController.signal,\n }),\n };\n }\n const coalescedRequest = coalescedRequestsByDeduplicationKey[deduplicationKey];\n coalescedRequest.numConsumers++;\n if (signal) {\n const responsePromise = coalescedRequest.responsePromise as Promise<TResponse>;\n return await new Promise<TResponse>((resolve, reject) => {\n const handleAbort = (e: AbortSignalEventMap['abort']) => {\n signal.removeEventListener('abort', handleAbort);\n coalescedRequest.numConsumers -= 1;\n if (coalescedRequest.numConsumers === 0) {\n const abortController = coalescedRequest.abortController;\n abortController.abort();\n }\n const abortError = new DOMException((e.target as AbortSignal).reason, 'AbortError');\n reject(abortError);\n };\n signal.addEventListener('abort', handleAbort);\n responsePromise.then(resolve).finally(() => {\n signal.removeEventListener('abort', handleAbort);\n });\n });\n } else {\n return (await coalescedRequest.responsePromise) as TResponse;\n }\n };\n}\n","// eslint-disable-next-line @typescript-eslint/ban-ts-comment\n// @ts-ignore\nimport fastStableStringify from 'fast-stable-stringify';\n\nexport function getSolanaRpcPayloadDeduplicationKey(payload: unknown): string | undefined {\n if (payload == null || typeof payload !== 'object' || Array.isArray(payload)) {\n return;\n }\n if ('jsonrpc' in payload && payload.jsonrpc === '2.0' && 'method' in payload && 'params' in payload) {\n return fastStableStringify([payload.method, payload.params]);\n }\n}\n"]}
|
|
@@ -0,0 +1,137 @@
|
|
|
1
|
+
export * from '@solana/instructions';
|
|
2
|
+
export * from '@solana/keys';
|
|
3
|
+
import { createSolanaRpcApi } from '@solana/rpc-core';
|
|
4
|
+
import { createJsonRpc, createHttpTransport } from '@solana/rpc-transport';
|
|
5
|
+
import fastStableStringify from 'fast-stable-stringify';
|
|
6
|
+
|
|
7
|
+
// src/index.ts
|
|
8
|
+
|
|
9
|
+
// src/rpc-integer-overflow-error.ts
|
|
10
|
+
var SolanaJsonRpcIntegerOverflowError = class extends Error {
|
|
11
|
+
constructor(methodName, keyPath, value) {
|
|
12
|
+
const argPosition = (typeof keyPath[0] === "number" ? keyPath[0] : parseInt(keyPath[0], 10)) + 1;
|
|
13
|
+
let ordinal = "";
|
|
14
|
+
const lastDigit = argPosition % 10;
|
|
15
|
+
const lastTwoDigits = argPosition % 100;
|
|
16
|
+
if (lastDigit == 1 && lastTwoDigits != 11) {
|
|
17
|
+
ordinal = argPosition + "st";
|
|
18
|
+
} else if (lastDigit == 2 && lastTwoDigits != 12) {
|
|
19
|
+
ordinal = argPosition + "nd";
|
|
20
|
+
} else if (lastDigit == 3 && lastTwoDigits != 13) {
|
|
21
|
+
ordinal = argPosition + "rd";
|
|
22
|
+
} else {
|
|
23
|
+
ordinal = argPosition + "th";
|
|
24
|
+
}
|
|
25
|
+
const path = keyPath.length > 1 ? keyPath.slice(1).map((pathPart) => typeof pathPart === "number" ? `[${pathPart}]` : pathPart).join(".") : null;
|
|
26
|
+
super(
|
|
27
|
+
`The ${ordinal} argument to the \`${methodName}\` RPC method${path ? ` at path \`${path}\`` : ""} was \`${value}\`. This number is unsafe for use with the Solana JSON-RPC because it exceeds \`Number.MAX_SAFE_INTEGER\`.`
|
|
28
|
+
);
|
|
29
|
+
this.keyPath = keyPath;
|
|
30
|
+
this.methodName = methodName;
|
|
31
|
+
this.value = value;
|
|
32
|
+
}
|
|
33
|
+
get name() {
|
|
34
|
+
return "SolanaJsonRpcIntegerOverflowError";
|
|
35
|
+
}
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
// src/rpc-default-config.ts
|
|
39
|
+
var DEFAULT_RPC_CONFIG = {
|
|
40
|
+
onIntegerOverflow(methodName, keyPath, value) {
|
|
41
|
+
throw new SolanaJsonRpcIntegerOverflowError(methodName, keyPath, value);
|
|
42
|
+
}
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
// src/rpc.ts
|
|
46
|
+
function createSolanaRpc(config) {
|
|
47
|
+
return createJsonRpc({
|
|
48
|
+
...config,
|
|
49
|
+
api: createSolanaRpcApi(DEFAULT_RPC_CONFIG)
|
|
50
|
+
});
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
// src/rpc-request-coalescer.ts
|
|
54
|
+
function getRpcTransportWithRequestCoalescing(transport, getDeduplicationKey) {
|
|
55
|
+
let coalescedRequestsByDeduplicationKey;
|
|
56
|
+
return async function makeCoalescedHttpRequest(config) {
|
|
57
|
+
const { payload, signal } = config;
|
|
58
|
+
const deduplicationKey = getDeduplicationKey(payload);
|
|
59
|
+
if (deduplicationKey === void 0) {
|
|
60
|
+
return await transport(config);
|
|
61
|
+
}
|
|
62
|
+
if (!coalescedRequestsByDeduplicationKey) {
|
|
63
|
+
Promise.resolve().then(() => {
|
|
64
|
+
coalescedRequestsByDeduplicationKey = void 0;
|
|
65
|
+
});
|
|
66
|
+
coalescedRequestsByDeduplicationKey = {};
|
|
67
|
+
}
|
|
68
|
+
if (coalescedRequestsByDeduplicationKey[deduplicationKey] == null) {
|
|
69
|
+
const abortController = new AbortController();
|
|
70
|
+
coalescedRequestsByDeduplicationKey[deduplicationKey] = {
|
|
71
|
+
abortController,
|
|
72
|
+
numConsumers: 0,
|
|
73
|
+
responsePromise: transport({
|
|
74
|
+
...config,
|
|
75
|
+
signal: abortController.signal
|
|
76
|
+
})
|
|
77
|
+
};
|
|
78
|
+
}
|
|
79
|
+
const coalescedRequest = coalescedRequestsByDeduplicationKey[deduplicationKey];
|
|
80
|
+
coalescedRequest.numConsumers++;
|
|
81
|
+
if (signal) {
|
|
82
|
+
const responsePromise = coalescedRequest.responsePromise;
|
|
83
|
+
return await new Promise((resolve, reject) => {
|
|
84
|
+
const handleAbort = (e) => {
|
|
85
|
+
signal.removeEventListener("abort", handleAbort);
|
|
86
|
+
coalescedRequest.numConsumers -= 1;
|
|
87
|
+
if (coalescedRequest.numConsumers === 0) {
|
|
88
|
+
const abortController = coalescedRequest.abortController;
|
|
89
|
+
abortController.abort();
|
|
90
|
+
}
|
|
91
|
+
const abortError = new DOMException(e.target.reason, "AbortError");
|
|
92
|
+
reject(abortError);
|
|
93
|
+
};
|
|
94
|
+
signal.addEventListener("abort", handleAbort);
|
|
95
|
+
responsePromise.then(resolve).finally(() => {
|
|
96
|
+
signal.removeEventListener("abort", handleAbort);
|
|
97
|
+
});
|
|
98
|
+
});
|
|
99
|
+
} else {
|
|
100
|
+
return await coalescedRequest.responsePromise;
|
|
101
|
+
}
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
function getSolanaRpcPayloadDeduplicationKey(payload) {
|
|
105
|
+
if (payload == null || typeof payload !== "object" || Array.isArray(payload)) {
|
|
106
|
+
return;
|
|
107
|
+
}
|
|
108
|
+
if ("jsonrpc" in payload && payload.jsonrpc === "2.0" && "method" in payload && "params" in payload) {
|
|
109
|
+
return fastStableStringify([payload.method, payload.params]);
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
// src/rpc-transport.ts
|
|
114
|
+
function normalizeHeaders(headers) {
|
|
115
|
+
const out = {};
|
|
116
|
+
for (const headerName in headers) {
|
|
117
|
+
out[headerName.toLowerCase()] = headers[headerName];
|
|
118
|
+
}
|
|
119
|
+
return out;
|
|
120
|
+
}
|
|
121
|
+
function createDefaultRpcTransport(config) {
|
|
122
|
+
return getRpcTransportWithRequestCoalescing(
|
|
123
|
+
createHttpTransport({
|
|
124
|
+
...config,
|
|
125
|
+
headers: {
|
|
126
|
+
...config.headers ? normalizeHeaders(config.headers) : void 0,
|
|
127
|
+
...{
|
|
128
|
+
// Keep these headers lowercase so they will override any user-supplied headers above.
|
|
129
|
+
"solana-client": `js/${"2.0.0-development"}` ?? "UNKNOWN"
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
}),
|
|
133
|
+
getSolanaRpcPayloadDeduplicationKey
|
|
134
|
+
);
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
export { createDefaultRpcTransport, createSolanaRpc };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/rpc.ts","../src/rpc-integer-overflow-error.ts","../src/rpc-default-config.ts","../src/rpc-transport.ts","../src/rpc-request-coalescer.ts","../src/rpc-request-deduplication.ts"],"names":[],"mappings":"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","sourcesContent":["export * from '@solana/instructions';\nexport * from '@solana/keys';\nexport * from './rpc';\nexport * from './rpc-transport';\n","import { createSolanaRpcApi, SolanaRpcMethods } from '@solana/rpc-core';\nimport { createJsonRpc } from '@solana/rpc-transport';\nimport type { Rpc } from '@solana/rpc-transport/dist/types/json-rpc-types';\n\nimport { DEFAULT_RPC_CONFIG } from './rpc-default-config';\n\nexport function createSolanaRpc(config: Omit<Parameters<typeof createJsonRpc>[0], 'api'>): Rpc<SolanaRpcMethods> {\n return createJsonRpc<SolanaRpcMethods>({\n ...config,\n api: createSolanaRpcApi(DEFAULT_RPC_CONFIG),\n });\n}\n","export class SolanaJsonRpcIntegerOverflowError extends Error {\n readonly methodName: string;\n readonly keyPath: (number | string)[];\n readonly value: bigint;\n constructor(methodName: string, keyPath: (number | string)[], value: bigint) {\n const argPosition = (typeof keyPath[0] === 'number' ? keyPath[0] : parseInt(keyPath[0], 10)) + 1;\n let ordinal = '';\n const lastDigit = argPosition % 10;\n const lastTwoDigits = argPosition % 100;\n if (lastDigit == 1 && lastTwoDigits != 11) {\n ordinal = argPosition + 'st';\n } else if (lastDigit == 2 && lastTwoDigits != 12) {\n ordinal = argPosition + 'nd';\n } else if (lastDigit == 3 && lastTwoDigits != 13) {\n ordinal = argPosition + 'rd';\n } else {\n ordinal = argPosition + 'th';\n }\n const path =\n keyPath.length > 1\n ? keyPath\n .slice(1)\n .map(pathPart => (typeof pathPart === 'number' ? `[${pathPart}]` : pathPart))\n .join('.')\n : null;\n super(\n `The ${ordinal} argument to the \\`${methodName}\\` RPC method` +\n `${path ? ` at path \\`${path}\\`` : ''} was \\`${value}\\`. This number is ` +\n 'unsafe for use with the Solana JSON-RPC because it exceeds ' +\n '`Number.MAX_SAFE_INTEGER`.'\n );\n this.keyPath = keyPath;\n this.methodName = methodName;\n this.value = value;\n }\n get name() {\n return 'SolanaJsonRpcIntegerOverflowError';\n }\n}\n","import { createSolanaRpcApi } from '@solana/rpc-core';\n\nimport { SolanaJsonRpcIntegerOverflowError } from './rpc-integer-overflow-error';\n\nexport const DEFAULT_RPC_CONFIG: Partial<Parameters<typeof createSolanaRpcApi>[0]> = {\n onIntegerOverflow(methodName, keyPath, value) {\n throw new SolanaJsonRpcIntegerOverflowError(methodName, keyPath, value);\n },\n};\n","import { createHttpTransport } from '@solana/rpc-transport';\nimport { IRpcTransport } from '@solana/rpc-transport/dist/types/transports/transport-types';\n\nimport { getRpcTransportWithRequestCoalescing } from './rpc-request-coalescer';\nimport { getSolanaRpcPayloadDeduplicationKey } from './rpc-request-deduplication';\n\n/**\n * Lowercasing header names makes it easier to override user-supplied headers.\n */\nfunction normalizeHeaders<T extends Record<string, string>>(\n headers: T\n): { [K in keyof T & string as Lowercase<K>]: T[K] } {\n const out: Record<string, string> = {};\n for (const headerName in headers) {\n out[headerName.toLowerCase()] = headers[headerName];\n }\n return out as { [K in keyof T & string as Lowercase<K>]: T[K] };\n}\n\nexport function createDefaultRpcTransport(config: Parameters<typeof createHttpTransport>[0]): IRpcTransport {\n return getRpcTransportWithRequestCoalescing(\n createHttpTransport({\n ...config,\n headers: {\n ...(config.headers ? normalizeHeaders(config.headers) : undefined),\n ...({\n // Keep these headers lowercase so they will override any user-supplied headers above.\n 'solana-client': `js/${__VERSION__}` ?? 'UNKNOWN',\n } as { [overrideHeader: string]: string }),\n },\n }),\n getSolanaRpcPayloadDeduplicationKey\n );\n}\n","import { IRpcTransport } from '@solana/rpc-transport/dist/types/transports/transport-types';\n\ntype CoalescedRequest = {\n readonly abortController: AbortController;\n numConsumers: number;\n readonly responsePromise: Promise<unknown>;\n};\n\ntype GetDeduplicationKeyFn = (payload: unknown) => string | undefined;\n\nexport function getRpcTransportWithRequestCoalescing(\n transport: IRpcTransport,\n getDeduplicationKey: GetDeduplicationKeyFn\n): IRpcTransport {\n let coalescedRequestsByDeduplicationKey: Record<string, CoalescedRequest> | undefined;\n return async function makeCoalescedHttpRequest<TResponse>(\n config: Parameters<IRpcTransport>[0]\n ): Promise<TResponse> {\n const { payload, signal } = config;\n const deduplicationKey = getDeduplicationKey(payload);\n if (deduplicationKey === undefined) {\n return await transport(config);\n }\n if (!coalescedRequestsByDeduplicationKey) {\n Promise.resolve().then(() => {\n coalescedRequestsByDeduplicationKey = undefined;\n });\n coalescedRequestsByDeduplicationKey = {};\n }\n if (coalescedRequestsByDeduplicationKey[deduplicationKey] == null) {\n const abortController = new AbortController();\n coalescedRequestsByDeduplicationKey[deduplicationKey] = {\n abortController,\n numConsumers: 0,\n responsePromise: transport<TResponse>({\n ...config,\n signal: abortController.signal,\n }),\n };\n }\n const coalescedRequest = coalescedRequestsByDeduplicationKey[deduplicationKey];\n coalescedRequest.numConsumers++;\n if (signal) {\n const responsePromise = coalescedRequest.responsePromise as Promise<TResponse>;\n return await new Promise<TResponse>((resolve, reject) => {\n const handleAbort = (e: AbortSignalEventMap['abort']) => {\n signal.removeEventListener('abort', handleAbort);\n coalescedRequest.numConsumers -= 1;\n if (coalescedRequest.numConsumers === 0) {\n const abortController = coalescedRequest.abortController;\n abortController.abort();\n }\n const abortError = new DOMException((e.target as AbortSignal).reason, 'AbortError');\n reject(abortError);\n };\n signal.addEventListener('abort', handleAbort);\n responsePromise.then(resolve).finally(() => {\n signal.removeEventListener('abort', handleAbort);\n });\n });\n } else {\n return (await coalescedRequest.responsePromise) as TResponse;\n }\n };\n}\n","// eslint-disable-next-line @typescript-eslint/ban-ts-comment\n// @ts-ignore\nimport fastStableStringify from 'fast-stable-stringify';\n\nexport function getSolanaRpcPayloadDeduplicationKey(payload: unknown): string | undefined {\n if (payload == null || typeof payload !== 'object' || Array.isArray(payload)) {\n return;\n }\n if ('jsonrpc' in payload && payload.jsonrpc === '2.0' && 'method' in payload && 'params' in payload) {\n return fastStableStringify([payload.method, payload.params]);\n }\n}\n"]}
|