@velocity-exchange/sdk 0.4.0 → 0.6.1
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 +3 -3
- package/lib/browser/adminClient.d.ts +52 -0
- package/lib/browser/adminClient.js +97 -0
- package/lib/browser/config.js +6 -7
- package/lib/browser/constants/numericConstants.d.ts +1 -1
- package/lib/browser/constants/numericConstants.js +1 -1
- package/lib/browser/decode/user.js +5 -1
- package/lib/browser/idl/velocity.d.ts +191 -15
- package/lib/browser/idl/velocity.json +192 -16
- package/lib/browser/orderSubscriber/OrderSubscriber.d.ts +1 -0
- package/lib/browser/orderSubscriber/OrderSubscriber.js +10 -4
- package/lib/browser/pyth/pythLazerSubscriber.js +37 -27
- package/lib/browser/types.d.ts +6 -0
- package/lib/browser/user.d.ts +20 -3
- package/lib/browser/user.js +52 -4
- package/lib/browser/velocityClient.d.ts +46 -10
- package/lib/browser/velocityClient.js +107 -35
- package/lib/node/adminClient.d.ts +52 -0
- package/lib/node/adminClient.d.ts.map +1 -1
- package/lib/node/adminClient.js +97 -0
- package/lib/node/config.d.ts.map +1 -1
- package/lib/node/config.js +6 -7
- package/lib/node/constants/numericConstants.d.ts +1 -1
- package/lib/node/constants/numericConstants.d.ts.map +1 -1
- package/lib/node/constants/numericConstants.js +1 -1
- package/lib/node/decode/user.d.ts.map +1 -1
- package/lib/node/decode/user.js +5 -1
- package/lib/node/idl/velocity.d.ts +191 -15
- package/lib/node/idl/velocity.d.ts.map +1 -1
- package/lib/node/idl/velocity.json +192 -16
- package/lib/node/orderSubscriber/OrderSubscriber.d.ts +1 -0
- package/lib/node/orderSubscriber/OrderSubscriber.d.ts.map +1 -1
- package/lib/node/orderSubscriber/OrderSubscriber.js +10 -4
- package/lib/node/pyth/pythLazerSubscriber.d.ts.map +1 -1
- package/lib/node/pyth/pythLazerSubscriber.js +37 -27
- package/lib/node/types.d.ts +6 -0
- package/lib/node/types.d.ts.map +1 -1
- package/lib/node/user.d.ts +20 -3
- package/lib/node/user.d.ts.map +1 -1
- package/lib/node/user.js +52 -4
- package/lib/node/velocityClient.d.ts +46 -10
- package/lib/node/velocityClient.d.ts.map +1 -1
- package/lib/node/velocityClient.js +107 -35
- package/package.json +7 -3
- package/.prettierignore +0 -1
- package/CHANGELOG.md +0 -132
- package/build-browser.js +0 -58
- package/bunfig.toml +0 -3
- package/esbuild-shims.js +0 -12
- package/scripts/deposit-isolated-positions.ts +0 -110
- package/scripts/find-flagged-users.ts +0 -213
- package/scripts/grpc-client-test-comparison.ts +0 -372
- package/scripts/grpc-multiuser-client-test-comparison.ts +0 -158
- package/scripts/postbuild.js +0 -95
- package/scripts/single-grpc-client-test.ts +0 -284
- package/scripts/withdraw-isolated-positions.ts +0 -174
- package/src/accounts/README_WebSocketAccountSubscriberV2.md +0 -95
- package/src/accounts/README_WebSocketProgramAccountSubscriberV2.md +0 -135
- package/src/accounts/basicUserAccountSubscriber.ts +0 -79
- package/src/accounts/basicUserStatsAccountSubscriber.ts +0 -87
- package/src/accounts/bulkAccountLoader.ts +0 -358
- package/src/accounts/bulkUserStatsSubscription.ts +0 -40
- package/src/accounts/bulkUserSubscription.ts +0 -39
- package/src/accounts/customizedCadenceBulkAccountLoader.ts +0 -250
- package/src/accounts/fetch.ts +0 -200
- package/src/accounts/grpcAccountSubscriber.ts +0 -225
- package/src/accounts/grpcInsuranceFundStakeAccountSubscriber.ts +0 -73
- package/src/accounts/grpcMultiAccountSubscriber.ts +0 -566
- package/src/accounts/grpcMultiUserAccountSubscriber.ts +0 -328
- package/src/accounts/grpcProgramAccountSubscriber.ts +0 -264
- package/src/accounts/grpcUserAccountSubscriber.ts +0 -63
- package/src/accounts/grpcUserStatsAccountSubscriber.ts +0 -65
- package/src/accounts/grpcVelocityClientAccountSubscriber.ts +0 -257
- package/src/accounts/grpcVelocityClientAccountSubscriberV2.ts +0 -941
- package/src/accounts/laserProgramAccountSubscriber.ts +0 -266
- package/src/accounts/oneShotUserAccountSubscriber.ts +0 -88
- package/src/accounts/oneShotUserStatsAccountSubscriber.ts +0 -94
- package/src/accounts/pollingInsuranceFundStakeAccountSubscriber.ts +0 -223
- package/src/accounts/pollingOracleAccountSubscriber.ts +0 -151
- package/src/accounts/pollingTokenAccountSubscriber.ts +0 -147
- package/src/accounts/pollingUserAccountSubscriber.ts +0 -198
- package/src/accounts/pollingUserStatsAccountSubscriber.ts +0 -180
- package/src/accounts/pollingVelocityClientAccountSubscriber.ts +0 -774
- package/src/accounts/testBulkAccountLoader.ts +0 -59
- package/src/accounts/types.ts +0 -428
- package/src/accounts/utils.ts +0 -90
- package/src/accounts/webSocketAccountSubscriber.ts +0 -304
- package/src/accounts/webSocketAccountSubscriberV2.ts +0 -536
- package/src/accounts/webSocketInsuranceFundStakeAccountSubscriber.ts +0 -171
- package/src/accounts/webSocketProgramAccountSubscriber.ts +0 -244
- package/src/accounts/webSocketProgramAccountSubscriberV2.ts +0 -1048
- package/src/accounts/webSocketProgramAccountsSubscriberV2.ts +0 -1042
- package/src/accounts/webSocketUserAccountSubscriber.ts +0 -139
- package/src/accounts/webSocketUserStatsAccountSubsriber.ts +0 -131
- package/src/accounts/webSocketVelocityClientAccountSubscriber.ts +0 -865
- package/src/accounts/webSocketVelocityClientAccountSubscriberV2.ts +0 -897
- package/src/accounts/websocketProgramUserAccountSubscriber.ts +0 -127
- package/src/addresses/marketAddresses.ts +0 -28
- package/src/addresses/pda.ts +0 -620
- package/src/adminClient.ts +0 -8136
- package/src/assert/assert.ts +0 -5
- package/src/auctionSubscriber/auctionSubscriber.ts +0 -86
- package/src/auctionSubscriber/auctionSubscriberGrpc.ts +0 -99
- package/src/auctionSubscriber/index.ts +0 -9
- package/src/auctionSubscriber/types.ts +0 -30
- package/src/bankrun/bankrunConnection.ts +0 -630
- package/src/blockhashSubscriber/BlockhashSubscriber.ts +0 -160
- package/src/blockhashSubscriber/index.ts +0 -6
- package/src/blockhashSubscriber/types.ts +0 -13
- package/src/clock/clockSubscriber.ts +0 -146
- package/src/config.ts +0 -312
- package/src/constants/index.ts +0 -9
- package/src/constants/numericConstants.ts +0 -194
- package/src/constants/perpMarkets.ts +0 -127
- package/src/constants/spotMarkets.ts +0 -104
- package/src/constants/txConstants.ts +0 -2
- package/src/constituentMap/constituentMap.ts +0 -305
- package/src/constituentMap/pollingConstituentAccountSubscriber.ts +0 -99
- package/src/constituentMap/webSocketConstituentAccountSubscriber.ts +0 -121
- package/src/core/VelocityCore.ts +0 -606
- package/src/core/index.ts +0 -12
- package/src/core/instructions/deposit.ts +0 -64
- package/src/core/instructions/fill.ts +0 -51
- package/src/core/instructions/funding.ts +0 -33
- package/src/core/instructions/liquidation.ts +0 -55
- package/src/core/instructions/orders.ts +0 -84
- package/src/core/instructions/perpOrders.ts +0 -312
- package/src/core/instructions/settlement.ts +0 -40
- package/src/core/instructions/trigger.ts +0 -41
- package/src/core/instructions/withdraw.ts +0 -65
- package/src/core/remainingAccounts.ts +0 -320
- package/src/core/signedMsg.ts +0 -109
- package/src/decode/customCoder.ts +0 -148
- package/src/decode/user.ts +0 -401
- package/src/dlob/DLOB.ts +0 -2793
- package/src/dlob/DLOBNode.ts +0 -305
- package/src/dlob/DLOBSubscriber.ts +0 -269
- package/src/dlob/NodeList.ts +0 -244
- package/src/dlob/orderBookLevels.ts +0 -695
- package/src/dlob/types.ts +0 -37
- package/src/events/eventList.ts +0 -114
- package/src/events/eventSubscriber.ts +0 -521
- package/src/events/eventsServerLogProvider.ts +0 -189
- package/src/events/fetchLogs.ts +0 -219
- package/src/events/parse.ts +0 -271
- package/src/events/pollingLogProvider.ts +0 -113
- package/src/events/sort.ts +0 -51
- package/src/events/txEventCache.ts +0 -92
- package/src/events/types.ts +0 -337
- package/src/events/webSocketLogProvider.ts +0 -152
- package/src/factory/bigNum.ts +0 -709
- package/src/factory/oracleClient.ts +0 -73
- package/src/idl/pyth.json +0 -142
- package/src/idl/pyth.ts +0 -97
- package/src/idl/pyth_solana_receiver.json +0 -628
- package/src/idl/token_faucet.json +0 -229
- package/src/idl/token_faucet.ts +0 -197
- package/src/idl/velocity.json +0 -23974
- package/src/idl/velocity.ts +0 -23980
- package/src/index.ts +0 -150
- package/src/indicative-quotes/indicativeQuotesSender.ts +0 -233
- package/src/isomorphic/README.md +0 -19
- package/src/isomorphic/anchor.browser.ts +0 -44
- package/src/isomorphic/anchor.node.ts +0 -1
- package/src/isomorphic/anchor.ts +0 -1
- package/src/isomorphic/anchor29.browser.ts +0 -24
- package/src/isomorphic/anchor29.node.ts +0 -1
- package/src/isomorphic/anchor29.ts +0 -1
- package/src/isomorphic/grpc.browser.ts +0 -4
- package/src/isomorphic/grpc.node.ts +0 -130
- package/src/isomorphic/grpc.ts +0 -1
- package/src/jupiter/jupiterClient.ts +0 -502
- package/src/keypair.ts +0 -32
- package/src/margin/README.md +0 -138
- package/src/marginCalculation.ts +0 -407
- package/src/marinade/idl/idl.json +0 -1962
- package/src/marinade/index.ts +0 -73
- package/src/marinade/types.ts +0 -3925
- package/src/math/amm.ts +0 -1758
- package/src/math/auction.ts +0 -480
- package/src/math/bankruptcy.ts +0 -138
- package/src/math/builder.ts +0 -130
- package/src/math/conversion.ts +0 -45
- package/src/math/exchangeStatus.ts +0 -261
- package/src/math/funding.ts +0 -498
- package/src/math/insurance.ts +0 -171
- package/src/math/liquidation.ts +0 -433
- package/src/math/margin.ts +0 -327
- package/src/math/market.ts +0 -487
- package/src/math/oracles.ts +0 -477
- package/src/math/orders.ts +0 -500
- package/src/math/position.ts +0 -381
- package/src/math/repeg.ts +0 -223
- package/src/math/spotBalance.ts +0 -996
- package/src/math/spotMarket.ts +0 -115
- package/src/math/spotPosition.ts +0 -263
- package/src/math/state.ts +0 -71
- package/src/math/superStake.ts +0 -602
- package/src/math/tiers.ts +0 -73
- package/src/math/trade.ts +0 -879
- package/src/math/utils.ts +0 -183
- package/src/memcmp.ts +0 -279
- package/src/oracles/oracleClientCache.ts +0 -41
- package/src/oracles/oracleId.ts +0 -99
- package/src/oracles/prelaunchOracleClient.ts +0 -63
- package/src/oracles/pythClient.ts +0 -125
- package/src/oracles/pythLazerClient.ts +0 -141
- package/src/oracles/quoteAssetOracleClient.ts +0 -43
- package/src/oracles/strictOraclePrice.ts +0 -40
- package/src/oracles/types.ts +0 -82
- package/src/oracles/utils.ts +0 -45
- package/src/orderParams.ts +0 -117
- package/src/orderSubscriber/OrderSubscriber.ts +0 -378
- package/src/orderSubscriber/PollingSubscription.ts +0 -50
- package/src/orderSubscriber/WebsocketSubscription.ts +0 -137
- package/src/orderSubscriber/grpcSubscription.ts +0 -155
- package/src/orderSubscriber/index.ts +0 -7
- package/src/orderSubscriber/types.ts +0 -64
- package/src/priorityFee/averageOverSlotsStrategy.ts +0 -17
- package/src/priorityFee/averageStrategy.ts +0 -13
- package/src/priorityFee/ewmaStrategy.ts +0 -51
- package/src/priorityFee/heliusPriorityFeeMethod.ts +0 -68
- package/src/priorityFee/index.ts +0 -16
- package/src/priorityFee/maxOverSlotsStrategy.ts +0 -18
- package/src/priorityFee/maxStrategy.ts +0 -8
- package/src/priorityFee/priorityFeeSubscriber.ts +0 -328
- package/src/priorityFee/priorityFeeSubscriberMap.ts +0 -134
- package/src/priorityFee/solanaPriorityFeeMethod.ts +0 -46
- package/src/priorityFee/types.ts +0 -82
- package/src/priorityFee/velocityPriorityFeeMethod.ts +0 -53
- package/src/pyth/constants.ts +0 -9
- package/src/pyth/index.ts +0 -15
- package/src/pyth/pythLazerSubscriber.ts +0 -365
- package/src/pyth/types.ts +0 -4451
- package/src/pyth/utils.ts +0 -13
- package/src/slot/SlotSubscriber.ts +0 -126
- package/src/slot/SlothashSubscriber.ts +0 -163
- package/src/swap/UnifiedSwapClient.ts +0 -315
- package/src/swift/grpcSignedMsgUserAccountSubscriber.ts +0 -81
- package/src/swift/index.ts +0 -10
- package/src/swift/signedMsgUserAccountSubscriber.ts +0 -251
- package/src/swift/swiftOrderSubscriber.ts +0 -351
- package/src/testClient.ts +0 -42
- package/src/titan/titanClient.ts +0 -438
- package/src/token/index.ts +0 -13
- package/src/tokenFaucet.ts +0 -296
- package/src/tx/baseTxSender.ts +0 -651
- package/src/tx/blockhashFetcher/baseBlockhashFetcher.ts +0 -31
- package/src/tx/blockhashFetcher/cachedBlockhashFetcher.ts +0 -105
- package/src/tx/blockhashFetcher/types.ts +0 -9
- package/src/tx/fastSingleTxSender.ts +0 -200
- package/src/tx/forwardOnlyTxSender.ts +0 -193
- package/src/tx/priorityFeeCalculator.ts +0 -117
- package/src/tx/reportTransactionError.ts +0 -176
- package/src/tx/retryTxSender.ts +0 -177
- package/src/tx/txHandler.ts +0 -1009
- package/src/tx/txParamProcessor.ts +0 -225
- package/src/tx/types.ts +0 -117
- package/src/tx/utils.ts +0 -133
- package/src/tx/whileValidTxSender.ts +0 -377
- package/src/types.ts +0 -2575
- package/src/user.ts +0 -5316
- package/src/userConfig.ts +0 -38
- package/src/userMap/PollingSubscription.ts +0 -61
- package/src/userMap/WebsocketSubscription.ts +0 -93
- package/src/userMap/grpcSubscription.ts +0 -93
- package/src/userMap/referrerMap.ts +0 -360
- package/src/userMap/revenueShareEscrowMap.ts +0 -342
- package/src/userMap/userMap.ts +0 -784
- package/src/userMap/userMapConfig.ts +0 -82
- package/src/userMap/userStatsMap.ts +0 -393
- package/src/userName.ts +0 -37
- package/src/userStats.ts +0 -159
- package/src/userStatsConfig.ts +0 -35
- package/src/util/TransactionConfirmationManager.ts +0 -333
- package/src/util/chainClock.ts +0 -65
- package/src/util/computeUnits.ts +0 -101
- package/src/util/digest.ts +0 -33
- package/src/util/ed25519Utils.ts +0 -95
- package/src/util/promiseTimeout.ts +0 -23
- package/src/velocityClient.ts +0 -14802
- package/src/velocityClientConfig.ts +0 -119
- package/src/wallet.ts +0 -91
- package/tests/VelocityCore/builder_escrow.test.ts +0 -121
- package/tests/VelocityCore/decode.test.ts +0 -16
- package/tests/VelocityCore/fill_trigger.test.ts +0 -73
- package/tests/VelocityCore/instructions.test.ts +0 -46
- package/tests/VelocityCore/pdas.test.ts +0 -30
- package/tests/VelocityCore/perp_orders.test.ts +0 -205
- package/tests/VelocityCore/remainingAccounts.test.ts +0 -72
- package/tests/VelocityCore/settlement_liquidation.test.ts +0 -69
- package/tests/accounts/customizedCadenceBulkAccountLoader.test.ts +0 -211
- package/tests/amm/test.ts +0 -2402
- package/tests/auctions/test.ts +0 -81
- package/tests/bn/test.ts +0 -355
- package/tests/builder/builderFee.test.ts +0 -42
- package/tests/ci/verifyConstants.ts +0 -393
- package/tests/decode/test.ts +0 -262
- package/tests/decode/userAccountBufferStrings.ts +0 -102
- package/tests/dlob/helpers.ts +0 -748
- package/tests/dlob/test.ts +0 -6969
- package/tests/dlob/tickSizeStandardization.ts +0 -545
- package/tests/events/parseLogsForCuUsage.ts +0 -139
- package/tests/exchangeStatus/test.ts +0 -45
- package/tests/insurance/test.ts +0 -40
- package/tests/liquidation/test.ts +0 -125
- package/tests/oracles/mmOracleGate.test.ts +0 -379
- package/tests/oracles/pythPegSnap.test.ts +0 -76
- package/tests/sdkParity/enumParity.test.ts +0 -84
- package/tests/sdkParity/marginCategoryFill.test.ts +0 -143
- package/tests/sdkParity/memcmpOffsets.test.ts +0 -139
- package/tests/spot/test.ts +0 -281
- package/tests/tx/TransactionConfirmationManager.test.ts +0 -312
- package/tests/tx/cachedBlockhashFetcher.test.ts +0 -96
- package/tests/tx/priorityFeeCalculator.ts +0 -77
- package/tests/tx/priorityFeeStrategy.ts +0 -95
- package/tests/user/bankruptcy.ts +0 -165
- package/tests/user/feeAndWithdrawLimits.ts +0 -284
- package/tests/user/getMarginCalculation.ts +0 -586
- package/tests/user/helpers.ts +0 -184
- package/tests/user/liquidations.ts +0 -129
- package/tests/user/marginCalculations.test.ts +0 -321
- package/tests/user/test.ts +0 -833
- package/tsconfig.browser.json +0 -18
- package/tsconfig.json +0 -36
|
@@ -1,328 +0,0 @@
|
|
|
1
|
-
import { Connection, PublicKey } from '@solana/web3.js';
|
|
2
|
-
import {
|
|
3
|
-
DEFAULT_PRIORITY_FEE_MAP_FREQUENCY_MS,
|
|
4
|
-
PriorityFeeMethod,
|
|
5
|
-
PriorityFeeStrategy,
|
|
6
|
-
PriorityFeeSubscriberConfig,
|
|
7
|
-
} from './types';
|
|
8
|
-
import { AverageOverSlotsStrategy } from './averageOverSlotsStrategy';
|
|
9
|
-
import { MaxOverSlotsStrategy } from './maxOverSlotsStrategy';
|
|
10
|
-
import { fetchSolanaPriorityFee } from './solanaPriorityFeeMethod';
|
|
11
|
-
import {
|
|
12
|
-
HeliusPriorityFeeLevels,
|
|
13
|
-
HeliusPriorityLevel,
|
|
14
|
-
fetchHeliusPriorityFee,
|
|
15
|
-
} from './heliusPriorityFeeMethod';
|
|
16
|
-
import {
|
|
17
|
-
fetchVelocityPriorityFee,
|
|
18
|
-
VelocityMarketInfo,
|
|
19
|
-
} from './velocityPriorityFeeMethod';
|
|
20
|
-
|
|
21
|
-
/**
|
|
22
|
-
* PriorityFeeSubscriber — polls one of three sources (Solana RPC, Helius, or
|
|
23
|
-
* the Velocity-hosted priority fee cache — see `PriorityFeeMethod`) on an
|
|
24
|
-
* interval and exposes several aggregations over the resulting samples: a
|
|
25
|
-
* simple average, a max, and a caller-supplied `customStrategy`. All
|
|
26
|
-
* `get*StrategyResult` accessors return `0` until the first successful poll,
|
|
27
|
-
* and are clamped to `maxFeeMicroLamports` (if set) after applying
|
|
28
|
-
* `priorityFeeMultiplier`. All returned fee values are in micro-lamports per
|
|
29
|
-
* compute unit, the unit Solana's `ComputeBudgetProgram.setComputeUnitPrice`
|
|
30
|
-
* expects.
|
|
31
|
-
*/
|
|
32
|
-
export class PriorityFeeSubscriber {
|
|
33
|
-
connection?: Connection;
|
|
34
|
-
frequencyMs: number;
|
|
35
|
-
addresses: string[];
|
|
36
|
-
velocityMarkets?: VelocityMarketInfo[];
|
|
37
|
-
customStrategy?: PriorityFeeStrategy;
|
|
38
|
-
averageStrategy = new AverageOverSlotsStrategy();
|
|
39
|
-
maxStrategy = new MaxOverSlotsStrategy();
|
|
40
|
-
priorityFeeMethod = PriorityFeeMethod.SOLANA;
|
|
41
|
-
lookbackDistance: number;
|
|
42
|
-
maxFeeMicroLamports?: number;
|
|
43
|
-
priorityFeeMultiplier?: number;
|
|
44
|
-
|
|
45
|
-
velocityPriorityFeeEndpoint?: string;
|
|
46
|
-
heliusRpcUrl?: string;
|
|
47
|
-
lastHeliusSample?: HeliusPriorityFeeLevels;
|
|
48
|
-
|
|
49
|
-
intervalId?: ReturnType<typeof setTimeout>;
|
|
50
|
-
|
|
51
|
-
latestPriorityFee = 0;
|
|
52
|
-
lastCustomStrategyResult = 0;
|
|
53
|
-
lastAvgStrategyResult = 0;
|
|
54
|
-
lastMaxStrategyResult = 0;
|
|
55
|
-
lastSlotSeen = 0;
|
|
56
|
-
|
|
57
|
-
/**
|
|
58
|
-
* @param config See `PriorityFeeSubscriberConfig`. Required fields depend on `priorityFeeMethod` (default `SOLANA`): SOLANA needs `connection`; HELIUS needs `heliusRpcUrl` or a Helius `connection`; VELOCITY needs `velocityPriorityFeeEndpoint`.
|
|
59
|
-
* @throws If `priorityFeeMethod` is `HELIUS` without a resolvable Helius RPC URL, or `SOLANA` without a `connection`.
|
|
60
|
-
*/
|
|
61
|
-
public constructor(config: PriorityFeeSubscriberConfig) {
|
|
62
|
-
this.connection = config.connection;
|
|
63
|
-
this.frequencyMs =
|
|
64
|
-
config.frequencyMs ?? DEFAULT_PRIORITY_FEE_MAP_FREQUENCY_MS;
|
|
65
|
-
this.addresses = config.addresses
|
|
66
|
-
? config.addresses.map((address) => address.toBase58())
|
|
67
|
-
: [];
|
|
68
|
-
this.velocityMarkets = config.velocityMarkets;
|
|
69
|
-
|
|
70
|
-
if (config.customStrategy) {
|
|
71
|
-
this.customStrategy = config.customStrategy;
|
|
72
|
-
} else {
|
|
73
|
-
this.customStrategy = this.averageStrategy;
|
|
74
|
-
}
|
|
75
|
-
this.lookbackDistance = config.slotsToCheck ?? 50;
|
|
76
|
-
|
|
77
|
-
if (config.priorityFeeMethod) {
|
|
78
|
-
this.priorityFeeMethod = config.priorityFeeMethod;
|
|
79
|
-
|
|
80
|
-
if (this.priorityFeeMethod === PriorityFeeMethod.HELIUS) {
|
|
81
|
-
if (config.heliusRpcUrl === undefined) {
|
|
82
|
-
if (this.connection?.rpcEndpoint.includes('helius')) {
|
|
83
|
-
this.heliusRpcUrl = this.connection.rpcEndpoint;
|
|
84
|
-
} else {
|
|
85
|
-
throw new Error(
|
|
86
|
-
'Connection must be helius, or heliusRpcUrl must be provided to use PriorityFeeMethod.HELIUS'
|
|
87
|
-
);
|
|
88
|
-
}
|
|
89
|
-
} else {
|
|
90
|
-
this.heliusRpcUrl = config.heliusRpcUrl;
|
|
91
|
-
}
|
|
92
|
-
} else if (this.priorityFeeMethod === PriorityFeeMethod.VELOCITY) {
|
|
93
|
-
this.velocityPriorityFeeEndpoint =
|
|
94
|
-
config.velocityPriorityFeeEndpoint ??
|
|
95
|
-
config.velocityPriorityFeeEndpoint;
|
|
96
|
-
}
|
|
97
|
-
}
|
|
98
|
-
|
|
99
|
-
if (this.priorityFeeMethod === PriorityFeeMethod.SOLANA) {
|
|
100
|
-
if (this.connection === undefined) {
|
|
101
|
-
throw new Error(
|
|
102
|
-
'connection must be provided to use SOLANA priority fee API'
|
|
103
|
-
);
|
|
104
|
-
}
|
|
105
|
-
}
|
|
106
|
-
|
|
107
|
-
this.maxFeeMicroLamports = config.maxFeeMicroLamports;
|
|
108
|
-
this.priorityFeeMultiplier = config.priorityFeeMultiplier ?? 1.0;
|
|
109
|
-
}
|
|
110
|
-
|
|
111
|
-
/** Starts polling at `frequencyMs` and performs one immediate `load()`. Idempotent while already subscribed. */
|
|
112
|
-
public async subscribe(): Promise<void> {
|
|
113
|
-
if (this.intervalId) {
|
|
114
|
-
return;
|
|
115
|
-
}
|
|
116
|
-
|
|
117
|
-
this.intervalId = setInterval(this.load.bind(this), this.frequencyMs); // we set the intervalId first, preventing a side effect of unsubscribing failing during the race condition where unsubscribes happens before subscribe is finished
|
|
118
|
-
await this.load();
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
private async loadForSolana(): Promise<void> {
|
|
122
|
-
if (this.connection === undefined) {
|
|
123
|
-
throw new Error(
|
|
124
|
-
'connection must be provided to use SOLANA priority fee API'
|
|
125
|
-
);
|
|
126
|
-
}
|
|
127
|
-
const samples = await fetchSolanaPriorityFee(
|
|
128
|
-
this.connection,
|
|
129
|
-
this.lookbackDistance,
|
|
130
|
-
this.addresses
|
|
131
|
-
);
|
|
132
|
-
if (samples === undefined) {
|
|
133
|
-
throw new Error('fetchSolanaPriorityFee returned no samples');
|
|
134
|
-
}
|
|
135
|
-
if (samples.length > 0) {
|
|
136
|
-
this.latestPriorityFee = samples[0].prioritizationFee;
|
|
137
|
-
this.lastSlotSeen = samples[0].slot;
|
|
138
|
-
|
|
139
|
-
this.lastAvgStrategyResult = this.averageStrategy.calculate(samples);
|
|
140
|
-
this.lastMaxStrategyResult = this.maxStrategy.calculate(samples);
|
|
141
|
-
if (this.customStrategy) {
|
|
142
|
-
this.lastCustomStrategyResult = this.customStrategy.calculate(samples);
|
|
143
|
-
}
|
|
144
|
-
}
|
|
145
|
-
}
|
|
146
|
-
|
|
147
|
-
private async loadForHelius(): Promise<void> {
|
|
148
|
-
if (this.heliusRpcUrl === undefined) {
|
|
149
|
-
throw new Error(
|
|
150
|
-
'heliusRpcUrl must be provided to use PriorityFeeMethod.HELIUS'
|
|
151
|
-
);
|
|
152
|
-
}
|
|
153
|
-
const sample = await fetchHeliusPriorityFee(
|
|
154
|
-
this.heliusRpcUrl,
|
|
155
|
-
this.lookbackDistance,
|
|
156
|
-
this.addresses
|
|
157
|
-
);
|
|
158
|
-
this.lastHeliusSample = sample?.result?.priorityFeeLevels ?? undefined;
|
|
159
|
-
|
|
160
|
-
if (sample !== undefined && this.lastHeliusSample) {
|
|
161
|
-
this.lastAvgStrategyResult =
|
|
162
|
-
this.lastHeliusSample[HeliusPriorityLevel.MEDIUM];
|
|
163
|
-
this.lastMaxStrategyResult =
|
|
164
|
-
this.lastHeliusSample[HeliusPriorityLevel.UNSAFE_MAX];
|
|
165
|
-
if (this.customStrategy) {
|
|
166
|
-
this.lastCustomStrategyResult = this.customStrategy.calculate(sample);
|
|
167
|
-
}
|
|
168
|
-
}
|
|
169
|
-
}
|
|
170
|
-
|
|
171
|
-
private async loadForVelocity(): Promise<void> {
|
|
172
|
-
if (!this.velocityMarkets) {
|
|
173
|
-
return;
|
|
174
|
-
}
|
|
175
|
-
if (this.velocityPriorityFeeEndpoint === undefined) {
|
|
176
|
-
throw new Error(
|
|
177
|
-
'velocityPriorityFeeEndpoint must be provided to use PriorityFeeMethod.VELOCITY'
|
|
178
|
-
);
|
|
179
|
-
}
|
|
180
|
-
const sample = await fetchVelocityPriorityFee(
|
|
181
|
-
this.velocityPriorityFeeEndpoint,
|
|
182
|
-
this.velocityMarkets.map((m) => m.marketType),
|
|
183
|
-
this.velocityMarkets.map((m) => m.marketIndex)
|
|
184
|
-
);
|
|
185
|
-
if (sample.length > 0) {
|
|
186
|
-
// The endpoint returns one fee-level set per requested market. Take the
|
|
187
|
-
// max level across markets so a transaction touching several markets is
|
|
188
|
-
// covered by the most expensive one. (Base indexed the array itself with
|
|
189
|
-
// a string enum key — `sample['medium']` — which yielded `undefined` and
|
|
190
|
-
// produced NaN strategy results; the missing per-element index is fixed
|
|
191
|
-
// here.)
|
|
192
|
-
this.lastAvgStrategyResult = Math.max(
|
|
193
|
-
...sample.map((s) => s[HeliusPriorityLevel.MEDIUM])
|
|
194
|
-
);
|
|
195
|
-
this.lastMaxStrategyResult = Math.max(
|
|
196
|
-
...sample.map((s) => s[HeliusPriorityLevel.UNSAFE_MAX])
|
|
197
|
-
);
|
|
198
|
-
if (this.customStrategy) {
|
|
199
|
-
// Custom strategies expect `{ slot, prioritizationFee }[]`; map each
|
|
200
|
-
// market's medium level into that shape so they aggregate real values
|
|
201
|
-
// instead of summing the absent `prioritizationFee` field (NaN).
|
|
202
|
-
this.lastCustomStrategyResult = this.customStrategy.calculate(
|
|
203
|
-
sample.map((s) => ({
|
|
204
|
-
slot: 0,
|
|
205
|
-
prioritizationFee: s[HeliusPriorityLevel.MEDIUM],
|
|
206
|
-
}))
|
|
207
|
-
);
|
|
208
|
-
}
|
|
209
|
-
}
|
|
210
|
-
}
|
|
211
|
-
|
|
212
|
-
/** @returns The current clamp on returned fee values (micro-lamports/CU), or `undefined` if unclamped. */
|
|
213
|
-
public getMaxPriorityFee(): number | undefined {
|
|
214
|
-
return this.maxFeeMicroLamports;
|
|
215
|
-
}
|
|
216
|
-
|
|
217
|
-
/** Updates the clamp applied to all `get*StrategyResult`/`getHeliusPriorityFeeLevel` results. Pass `undefined` to remove the clamp. */
|
|
218
|
-
public updateMaxPriorityFee(newMaxFee: number | undefined) {
|
|
219
|
-
this.maxFeeMicroLamports = newMaxFee;
|
|
220
|
-
}
|
|
221
|
-
|
|
222
|
-
/** @returns The multiplier applied to strategy results before clamping; defaults to `1.0`. */
|
|
223
|
-
public getPriorityFeeMultiplier(): number {
|
|
224
|
-
return this.priorityFeeMultiplier ?? 1.0;
|
|
225
|
-
}
|
|
226
|
-
|
|
227
|
-
/** Updates the multiplier applied to `getCustomStrategyResult`/`getAvgStrategyResult`/`getMaxStrategyResult` before clamping. */
|
|
228
|
-
public updatePriorityFeeMultiplier(newPriorityFeeMultiplier: number) {
|
|
229
|
-
this.priorityFeeMultiplier = newPriorityFeeMultiplier;
|
|
230
|
-
}
|
|
231
|
-
|
|
232
|
-
/** Swaps the `PriorityFeeStrategy` used to compute `getCustomStrategyResult`; takes effect on the next `load()`. */
|
|
233
|
-
public updateCustomStrategy(newStrategy: PriorityFeeStrategy) {
|
|
234
|
-
this.customStrategy = newStrategy;
|
|
235
|
-
}
|
|
236
|
-
|
|
237
|
-
/**
|
|
238
|
-
* Only meaningful with `priorityFeeMethod: HELIUS`.
|
|
239
|
-
* @param level Helius percentile level to read; defaults to `MEDIUM`.
|
|
240
|
-
* @returns That level's fee (micro-lamports/CU) from the most recent Helius sample, clamped to `maxFeeMicroLamports` if set, or `0` if no sample has been loaded yet.
|
|
241
|
-
*/
|
|
242
|
-
public getHeliusPriorityFeeLevel(
|
|
243
|
-
level: HeliusPriorityLevel = HeliusPriorityLevel.MEDIUM
|
|
244
|
-
): number {
|
|
245
|
-
if (this.lastHeliusSample === undefined) {
|
|
246
|
-
return 0;
|
|
247
|
-
}
|
|
248
|
-
if (this.maxFeeMicroLamports !== undefined) {
|
|
249
|
-
return Math.min(this.maxFeeMicroLamports, this.lastHeliusSample[level]);
|
|
250
|
-
}
|
|
251
|
-
return this.lastHeliusSample[level];
|
|
252
|
-
}
|
|
253
|
-
|
|
254
|
-
/** @returns The configured `customStrategy`'s result from the most recent poll (micro-lamports/CU), scaled by `priorityFeeMultiplier` and clamped to `maxFeeMicroLamports` if set. `0` before the first successful `load()`. */
|
|
255
|
-
public getCustomStrategyResult(): number {
|
|
256
|
-
const result =
|
|
257
|
-
this.lastCustomStrategyResult * this.getPriorityFeeMultiplier();
|
|
258
|
-
if (this.maxFeeMicroLamports !== undefined) {
|
|
259
|
-
return Math.min(this.maxFeeMicroLamports, result);
|
|
260
|
-
}
|
|
261
|
-
return result;
|
|
262
|
-
}
|
|
263
|
-
|
|
264
|
-
/** @returns The average-over-samples fee from the most recent poll (micro-lamports/CU) — for HELIUS this is the MEDIUM level, for VELOCITY the max MEDIUM level across configured markets — scaled by `priorityFeeMultiplier` and clamped to `maxFeeMicroLamports` if set. `0` before the first successful `load()`. */
|
|
265
|
-
public getAvgStrategyResult(): number {
|
|
266
|
-
const result = this.lastAvgStrategyResult * this.getPriorityFeeMultiplier();
|
|
267
|
-
if (this.maxFeeMicroLamports !== undefined) {
|
|
268
|
-
return Math.min(this.maxFeeMicroLamports, result);
|
|
269
|
-
}
|
|
270
|
-
return result;
|
|
271
|
-
}
|
|
272
|
-
|
|
273
|
-
/** @returns The max-over-samples fee from the most recent poll (micro-lamports/CU) — for HELIUS this is the UNSAFE_MAX level, for VELOCITY the max UNSAFE_MAX level across configured markets — scaled by `priorityFeeMultiplier` and clamped to `maxFeeMicroLamports` if set. `0` before the first successful `load()`. */
|
|
274
|
-
public getMaxStrategyResult(): number {
|
|
275
|
-
const result = this.lastMaxStrategyResult * this.getPriorityFeeMultiplier();
|
|
276
|
-
if (this.maxFeeMicroLamports !== undefined) {
|
|
277
|
-
return Math.min(this.maxFeeMicroLamports, result);
|
|
278
|
-
}
|
|
279
|
-
return result;
|
|
280
|
-
}
|
|
281
|
-
|
|
282
|
-
/**
|
|
283
|
-
* Fetches one round of samples from the configured `priorityFeeMethod`
|
|
284
|
-
* and recomputes `latestPriorityFee`/`lastAvgStrategyResult`/
|
|
285
|
-
* `lastMaxStrategyResult`/`lastCustomStrategyResult`. Errors are caught
|
|
286
|
-
* and logged, not thrown, so a transient failure just leaves the previous
|
|
287
|
-
* values in place until the next poll.
|
|
288
|
-
*/
|
|
289
|
-
public async load(): Promise<void> {
|
|
290
|
-
try {
|
|
291
|
-
if (this.priorityFeeMethod === PriorityFeeMethod.SOLANA) {
|
|
292
|
-
await this.loadForSolana();
|
|
293
|
-
} else if (this.priorityFeeMethod === PriorityFeeMethod.HELIUS) {
|
|
294
|
-
await this.loadForHelius();
|
|
295
|
-
} else if (this.priorityFeeMethod === PriorityFeeMethod.VELOCITY) {
|
|
296
|
-
await this.loadForVelocity();
|
|
297
|
-
} else {
|
|
298
|
-
throw new Error(`${this.priorityFeeMethod} load not implemented`);
|
|
299
|
-
}
|
|
300
|
-
} catch (err) {
|
|
301
|
-
const e = err as Error;
|
|
302
|
-
console.error(
|
|
303
|
-
`Error loading priority fee ${this.priorityFeeMethod}: ${e.message}\n${
|
|
304
|
-
e.stack ? e.stack : ''
|
|
305
|
-
}`
|
|
306
|
-
);
|
|
307
|
-
return;
|
|
308
|
-
}
|
|
309
|
-
}
|
|
310
|
-
|
|
311
|
-
/** Stops polling. */
|
|
312
|
-
public async unsubscribe(): Promise<void> {
|
|
313
|
-
if (this.intervalId) {
|
|
314
|
-
clearInterval(this.intervalId);
|
|
315
|
-
this.intervalId = undefined;
|
|
316
|
-
}
|
|
317
|
-
}
|
|
318
|
-
|
|
319
|
-
/** Replaces the set of write-locked addresses used for SOLANA/HELIUS fee sampling; takes effect on the next `load()`. */
|
|
320
|
-
public updateAddresses(addresses: PublicKey[]) {
|
|
321
|
-
this.addresses = addresses.map((k) => k.toBase58());
|
|
322
|
-
}
|
|
323
|
-
|
|
324
|
-
/** Replaces the set of markets queried when `priorityFeeMethod` is VELOCITY; takes effect on the next `load()`. */
|
|
325
|
-
public updateMarketTypeAndIndex(velocityMarkets: VelocityMarketInfo[]) {
|
|
326
|
-
this.velocityMarkets = velocityMarkets;
|
|
327
|
-
}
|
|
328
|
-
}
|
|
@@ -1,134 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
VelocityMarketInfo,
|
|
3
|
-
VelocityPriorityFeeLevels,
|
|
4
|
-
VelocityPriorityFeeResponse,
|
|
5
|
-
fetchVelocityPriorityFee,
|
|
6
|
-
} from './velocityPriorityFeeMethod';
|
|
7
|
-
import {
|
|
8
|
-
DEFAULT_PRIORITY_FEE_MAP_FREQUENCY_MS,
|
|
9
|
-
PriorityFeeSubscriberMapConfig,
|
|
10
|
-
} from './types';
|
|
11
|
-
|
|
12
|
-
/**
|
|
13
|
-
* PriorityFeeSubscriberMap — polls the Velocity-hosted `/batchPriorityFees`
|
|
14
|
-
* endpoint for a fixed set of markets and caches the latest per-market fee
|
|
15
|
-
* levels, keyed by market type and index. Unlike `PriorityFeeSubscriber`
|
|
16
|
-
* (single aggregated result across `PriorityFeeMethod.VELOCITY` markets),
|
|
17
|
-
* this exposes each market's fee levels independently via `getPriorityFees`.
|
|
18
|
-
*/
|
|
19
|
-
export class PriorityFeeSubscriberMap {
|
|
20
|
-
frequencyMs: number;
|
|
21
|
-
intervalId?: ReturnType<typeof setTimeout>;
|
|
22
|
-
|
|
23
|
-
velocityMarkets?: VelocityMarketInfo[];
|
|
24
|
-
velocityPriorityFeeEndpoint: string;
|
|
25
|
-
feesMap: Map<string, Map<number, VelocityPriorityFeeLevels>>; // marketType -> marketIndex -> priority fee
|
|
26
|
-
|
|
27
|
-
/** @param config `frequencyMs` defaults to `DEFAULT_PRIORITY_FEE_MAP_FREQUENCY_MS` (10s); `velocityPriorityFeeEndpoint` is required. */
|
|
28
|
-
public constructor(config: PriorityFeeSubscriberMapConfig) {
|
|
29
|
-
this.frequencyMs =
|
|
30
|
-
config.frequencyMs ?? DEFAULT_PRIORITY_FEE_MAP_FREQUENCY_MS;
|
|
31
|
-
// Type-system guarantees at least one of the two is supplied.
|
|
32
|
-
this.velocityPriorityFeeEndpoint = (config.velocityPriorityFeeEndpoint ??
|
|
33
|
-
config.velocityPriorityFeeEndpoint)!;
|
|
34
|
-
this.velocityMarkets = config.velocityMarkets;
|
|
35
|
-
this.feesMap = new Map<string, Map<number, VelocityPriorityFeeLevels>>();
|
|
36
|
-
this.feesMap.set('perp', new Map<number, VelocityPriorityFeeLevels>());
|
|
37
|
-
this.feesMap.set('spot', new Map<number, VelocityPriorityFeeLevels>());
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
private updateFeesMap(
|
|
41
|
-
velocityPriorityFeeResponse: VelocityPriorityFeeResponse
|
|
42
|
-
) {
|
|
43
|
-
velocityPriorityFeeResponse.forEach((fee: VelocityPriorityFeeLevels) => {
|
|
44
|
-
this.feesMap.get(fee.marketType)!.set(fee.marketIndex, fee);
|
|
45
|
-
});
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
/** Performs an immediate `load()` and then polls at `frequencyMs`. Idempotent while already subscribed. */
|
|
49
|
-
public async subscribe(): Promise<void> {
|
|
50
|
-
if (this.intervalId) {
|
|
51
|
-
return;
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
await this.load();
|
|
55
|
-
this.intervalId = setInterval(this.load.bind(this), this.frequencyMs);
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
/** Stops polling. */
|
|
59
|
-
public async unsubscribe(): Promise<void> {
|
|
60
|
-
if (this.intervalId) {
|
|
61
|
-
clearInterval(this.intervalId);
|
|
62
|
-
this.intervalId = undefined;
|
|
63
|
-
}
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
/**
|
|
67
|
-
* Fetches one batch of per-market fee levels from
|
|
68
|
-
* `/batchPriorityFees` for all `velocityMarkets` and merges the results
|
|
69
|
-
* into `feesMap`. No-ops if no markets are configured. Errors are caught
|
|
70
|
-
* and logged, not thrown — `feesMap` is left at its previous state.
|
|
71
|
-
*/
|
|
72
|
-
public async load(): Promise<void> {
|
|
73
|
-
try {
|
|
74
|
-
if (!this.velocityMarkets || this.velocityMarkets.length === 0) {
|
|
75
|
-
return;
|
|
76
|
-
}
|
|
77
|
-
const fees = await fetchVelocityPriorityFee(
|
|
78
|
-
this.velocityPriorityFeeEndpoint,
|
|
79
|
-
this.velocityMarkets.map((m) => m.marketType),
|
|
80
|
-
this.velocityMarkets.map((m) => m.marketIndex)
|
|
81
|
-
);
|
|
82
|
-
this.updateFeesMap(fees);
|
|
83
|
-
} catch (e) {
|
|
84
|
-
console.error('Error fetching priority fees', e);
|
|
85
|
-
}
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
/** Replaces the set of markets to fetch fees for; takes effect on the next `load()`. */
|
|
89
|
-
public updateMarketTypeAndIndex(velocityMarkets: VelocityMarketInfo[]) {
|
|
90
|
-
this.velocityMarkets = velocityMarkets;
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
/**
|
|
94
|
-
* @param marketType `'perp'` or `'spot'`.
|
|
95
|
-
* @param marketIndex Market index within that market type.
|
|
96
|
-
* @returns The most recently fetched fee-level set for that market, or `undefined` if never fetched (including before the first successful `load()`).
|
|
97
|
-
*/
|
|
98
|
-
public getPriorityFees(
|
|
99
|
-
marketType: string,
|
|
100
|
-
marketIndex: number
|
|
101
|
-
): VelocityPriorityFeeLevels | undefined {
|
|
102
|
-
return this.feesMap.get(marketType)?.get(marketIndex);
|
|
103
|
-
}
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
/** Example usage:
|
|
107
|
-
async function main() {
|
|
108
|
-
const velocityMarkets: VelocityMarketInfo[] = [
|
|
109
|
-
{ marketType: 'perp', marketIndex: 0 },
|
|
110
|
-
{ marketType: 'perp', marketIndex: 1 },
|
|
111
|
-
{ marketType: 'spot', marketIndex: 2 }
|
|
112
|
-
];
|
|
113
|
-
|
|
114
|
-
const subscriber = new PriorityFeeSubscriberMap({
|
|
115
|
-
velocityPriorityFeeEndpoint: 'https://dlob.velocity.trade',
|
|
116
|
-
frequencyMs: 5000,
|
|
117
|
-
velocityMarkets
|
|
118
|
-
});
|
|
119
|
-
await subscriber.subscribe();
|
|
120
|
-
|
|
121
|
-
for (let i = 0; i < 20; i++) {
|
|
122
|
-
await new Promise(resolve => setTimeout(resolve, 1000));
|
|
123
|
-
velocityMarkets.forEach(market => {
|
|
124
|
-
const fees = subscriber.getPriorityFees(market.marketType, market.marketIndex);
|
|
125
|
-
console.log(`Priority fees for ${market.marketType} market ${market.marketIndex}:`, fees);
|
|
126
|
-
});
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
await subscriber.unsubscribe();
|
|
131
|
-
}
|
|
132
|
-
|
|
133
|
-
main().catch(console.error);
|
|
134
|
-
*/
|
|
@@ -1,46 +0,0 @@
|
|
|
1
|
-
import { Connection } from '@solana/web3.js';
|
|
2
|
-
|
|
3
|
-
/** One sample from Solana's `getRecentPrioritizationFees`. */
|
|
4
|
-
export type SolanaPriorityFeeResponse = {
|
|
5
|
-
slot: number;
|
|
6
|
-
/** Priority fee paid, in micro-lamports per compute unit. */
|
|
7
|
-
prioritizationFee: number;
|
|
8
|
-
};
|
|
9
|
-
|
|
10
|
-
/**
|
|
11
|
-
* Fetches recent prioritization fees for `addresses` via the Solana RPC
|
|
12
|
-
* `getRecentPrioritizationFees` method, then filters to the most recent
|
|
13
|
-
* `lookbackDistance` slots (relative to the newest returned slot, not the
|
|
14
|
-
* current chain tip) and sorts descending by slot.
|
|
15
|
-
* @param connection RPC connection.
|
|
16
|
-
* @param lookbackDistance Number of slots back from the newest sample to retain.
|
|
17
|
-
* @param addresses Account keys to scope the fee lookup to (accounts the transaction will write-lock).
|
|
18
|
-
* @returns Filtered, slot-descending samples; `undefined` if the RPC returned zero results; an empty array if the RPC call itself threw (error is logged, not thrown).
|
|
19
|
-
*/
|
|
20
|
-
export async function fetchSolanaPriorityFee(
|
|
21
|
-
connection: Connection,
|
|
22
|
-
lookbackDistance: number,
|
|
23
|
-
addresses: string[]
|
|
24
|
-
): Promise<SolanaPriorityFeeResponse[] | undefined> {
|
|
25
|
-
try {
|
|
26
|
-
// @ts-ignore
|
|
27
|
-
const rpcJSONResponse: any = await connection._rpcRequest(
|
|
28
|
-
'getRecentPrioritizationFees',
|
|
29
|
-
[addresses]
|
|
30
|
-
);
|
|
31
|
-
|
|
32
|
-
const results: SolanaPriorityFeeResponse[] = rpcJSONResponse?.result;
|
|
33
|
-
|
|
34
|
-
if (!results.length) return;
|
|
35
|
-
|
|
36
|
-
// Sort and filter results based on the slot lookback setting
|
|
37
|
-
const descResults = results.sort((a, b) => b.slot - a.slot);
|
|
38
|
-
const cutoffSlot = descResults[0].slot - lookbackDistance;
|
|
39
|
-
|
|
40
|
-
return descResults.filter((result) => result.slot >= cutoffSlot);
|
|
41
|
-
} catch (err) {
|
|
42
|
-
console.error(err);
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
return [];
|
|
46
|
-
}
|
package/src/priorityFee/types.ts
DELETED
|
@@ -1,82 +0,0 @@
|
|
|
1
|
-
import { Connection, PublicKey } from '@solana/web3.js';
|
|
2
|
-
import { SolanaPriorityFeeResponse } from './solanaPriorityFeeMethod';
|
|
3
|
-
import { HeliusPriorityFeeResponse } from './heliusPriorityFeeMethod';
|
|
4
|
-
import {
|
|
5
|
-
VelocityMarketInfo,
|
|
6
|
-
VelocityPriorityFeeResponse,
|
|
7
|
-
} from './velocityPriorityFeeMethod';
|
|
8
|
-
|
|
9
|
-
/** Default poll interval (ms) for `PriorityFeeSubscriber`/`PriorityFeeSubscriberMap` when `frequencyMs` is not configured. */
|
|
10
|
-
export const DEFAULT_PRIORITY_FEE_MAP_FREQUENCY_MS = 10_000;
|
|
11
|
-
|
|
12
|
-
/**
|
|
13
|
-
* A pluggable priority-fee aggregation function. `PriorityFeeSubscriber`
|
|
14
|
-
* calls `calculate` after each poll to derive `getCustomStrategyResult()`.
|
|
15
|
-
* Built-in implementations: `AverageStrategy`/`AverageOverSlotsStrategy`,
|
|
16
|
-
* `EwmaStrategy`, `MaxStrategy`/`MaxOverSlotsStrategy`.
|
|
17
|
-
*/
|
|
18
|
-
export interface PriorityFeeStrategy {
|
|
19
|
-
// calculate the priority fee for a given set of samples.
|
|
20
|
-
// when samples is an array (SOLANA), expect it sorted in descending order (by slot)
|
|
21
|
-
/**
|
|
22
|
-
* @param samples Fee samples from whichever `priorityFeeMethod` is active — `SolanaPriorityFeeResponse[]` for SOLANA (expected sorted descending by slot), a single `HeliusPriorityFeeResponse` for HELIUS, or `VelocityPriorityFeeResponse` for VELOCITY.
|
|
23
|
-
* @returns A priority fee estimate in micro-lamports per compute unit.
|
|
24
|
-
*/
|
|
25
|
-
calculate(
|
|
26
|
-
samples:
|
|
27
|
-
| SolanaPriorityFeeResponse[]
|
|
28
|
-
| HeliusPriorityFeeResponse
|
|
29
|
-
| VelocityPriorityFeeResponse
|
|
30
|
-
): number;
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
/** Which upstream API `PriorityFeeSubscriber` queries for priority-fee samples. */
|
|
34
|
-
export enum PriorityFeeMethod {
|
|
35
|
-
/** Solana RPC `getRecentPrioritizationFees`. Requires `connection`. */
|
|
36
|
-
SOLANA = 'solana',
|
|
37
|
-
/** Helius `getPriorityFeeEstimate`. Requires `heliusRpcUrl` or a Helius `connection`. */
|
|
38
|
-
HELIUS = 'helius',
|
|
39
|
-
/** Velocity-hosted priority fee cache, scoped by market. Requires `velocityPriorityFeeEndpoint` and `velocityMarkets`. */
|
|
40
|
-
VELOCITY = 'velocity',
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
/** Configuration for `PriorityFeeSubscriber`. Which fields are required depends on `priorityFeeMethod` — see `PriorityFeeMethod`. */
|
|
44
|
-
export type PriorityFeeSubscriberConfig = {
|
|
45
|
-
/** RPC connection used for SOLANA sampling (and as a Helius URL source for HELIUS if `heliusRpcUrl` is omitted); optional only when `priorityFeeMethod` is `HELIUS` or `VELOCITY`. */
|
|
46
|
-
connection?: Connection;
|
|
47
|
-
/** Poll interval in milliseconds for `load()`; defaults to `DEFAULT_PRIORITY_FEE_MAP_FREQUENCY_MS` (10s). */
|
|
48
|
-
frequencyMs?: number;
|
|
49
|
-
/** Account keys the transaction will write-lock; scopes SOLANA/HELIUS fee sampling to congestion on these accounts specifically. */
|
|
50
|
-
addresses?: PublicKey[];
|
|
51
|
-
/** Markets to query when `priorityFeeMethod` is `VELOCITY`; can also be supplied later via `updateMarketTypeAndIndex`. */
|
|
52
|
-
velocityMarkets?: VelocityMarketInfo[];
|
|
53
|
-
/** `PriorityFeeStrategy` backing `getCustomStrategyResult()`; defaults to `AverageOverSlotsStrategy`. */
|
|
54
|
-
customStrategy?: PriorityFeeStrategy;
|
|
55
|
-
/** Which upstream API to sample from; defaults to `PriorityFeeMethod.SOLANA`. */
|
|
56
|
-
priorityFeeMethod?: PriorityFeeMethod;
|
|
57
|
-
/** Number of recent slots to consider when computing fee estimates; defaults to 50. */
|
|
58
|
-
slotsToCheck?: number;
|
|
59
|
-
/** Helius RPC URL; required for `PriorityFeeMethod.HELIUS` unless `connection`'s endpoint already points at Helius. */
|
|
60
|
-
heliusRpcUrl?: string;
|
|
61
|
-
/** Base URL of the Velocity-hosted priority fee service; required for `PriorityFeeMethod.VELOCITY`. */
|
|
62
|
-
velocityPriorityFeeEndpoint?: string;
|
|
63
|
-
/** Upper bound (micro-lamports per compute unit) applied to every `get*StrategyResult`/`getHeliusPriorityFeeLevel` return value, after `priorityFeeMultiplier`. Unset (`undefined`) means no clamp. */
|
|
64
|
-
maxFeeMicroLamports?: number;
|
|
65
|
-
/** Multiplier applied to the raw strategy result before `maxFeeMicroLamports` clamping; defaults to `1.0`. */
|
|
66
|
-
priorityFeeMultiplier?: number;
|
|
67
|
-
};
|
|
68
|
-
|
|
69
|
-
/** Base config for `PriorityFeeSubscriberMap`, which only supports `PriorityFeeMethod.VELOCITY` (batched per-market fee lookups via `/batchPriorityFees`). */
|
|
70
|
-
type PriorityFeeSubscriberMapConfigBase = {
|
|
71
|
-
/** Poll interval in milliseconds for `load()`; defaults to `DEFAULT_PRIORITY_FEE_MAP_FREQUENCY_MS` (10s). */
|
|
72
|
-
frequencyMs?: number;
|
|
73
|
-
/** Markets to fetch fees for; can also be supplied later via `updateMarketTypeAndIndex`. */
|
|
74
|
-
velocityMarkets?: VelocityMarketInfo[];
|
|
75
|
-
};
|
|
76
|
-
|
|
77
|
-
/** Configuration for `PriorityFeeSubscriberMap`. */
|
|
78
|
-
export type PriorityFeeSubscriberMapConfig =
|
|
79
|
-
PriorityFeeSubscriberMapConfigBase & {
|
|
80
|
-
/** Base URL of the Velocity-hosted priority fee service (queried via `/batchPriorityFees`). */
|
|
81
|
-
velocityPriorityFeeEndpoint: string;
|
|
82
|
-
};
|
|
@@ -1,53 +0,0 @@
|
|
|
1
|
-
import fetch from 'node-fetch';
|
|
2
|
-
import { HeliusPriorityLevel } from './heliusPriorityFeeMethod';
|
|
3
|
-
|
|
4
|
-
/** Identifies a market to fetch/track priority fees for. */
|
|
5
|
-
export type VelocityMarketInfo = {
|
|
6
|
-
marketType: string;
|
|
7
|
-
marketIndex: number;
|
|
8
|
-
};
|
|
9
|
-
|
|
10
|
-
/** Per-percentile priority fee (micro-lamports/CU, same buckets as `HeliusPriorityLevel`) for one market, as returned by the Velocity priority fee endpoint. */
|
|
11
|
-
export type VelocityPriorityFeeLevels = {
|
|
12
|
-
[key in HeliusPriorityLevel]: number;
|
|
13
|
-
} & {
|
|
14
|
-
marketType: 'perp' | 'spot';
|
|
15
|
-
marketIndex: number;
|
|
16
|
-
};
|
|
17
|
-
|
|
18
|
-
/** One `VelocityPriorityFeeLevels` entry per requested market. */
|
|
19
|
-
export type VelocityPriorityFeeResponse = VelocityPriorityFeeLevels[];
|
|
20
|
-
|
|
21
|
-
/**
|
|
22
|
-
* Fetches per-market priority fee levels from the Velocity-hosted
|
|
23
|
-
* `/batchPriorityFees` endpoint.
|
|
24
|
-
* @param url Base URL of the Velocity priority fee service.
|
|
25
|
-
* @param marketTypes Market types to query, parallel-indexed to `marketIndexes` (e.g. `['perp', 'perp', 'spot']`).
|
|
26
|
-
* @param marketIndexes Market indexes to query, parallel-indexed to `marketTypes`.
|
|
27
|
-
* @returns One `VelocityPriorityFeeLevels` per requested market; an empty array if the request failed (error is logged, not thrown) or returned a non-OK HTTP status.
|
|
28
|
-
*/
|
|
29
|
-
export async function fetchVelocityPriorityFee(
|
|
30
|
-
url: string,
|
|
31
|
-
marketTypes: string[],
|
|
32
|
-
marketIndexes: number[]
|
|
33
|
-
): Promise<VelocityPriorityFeeResponse> {
|
|
34
|
-
try {
|
|
35
|
-
const response = await fetch(
|
|
36
|
-
`${url}/batchPriorityFees?marketType=${marketTypes.join(
|
|
37
|
-
','
|
|
38
|
-
)}&marketIndex=${marketIndexes.join(',')}`
|
|
39
|
-
);
|
|
40
|
-
if (!response.ok) {
|
|
41
|
-
throw new Error(`HTTP error! status: ${response.status}`);
|
|
42
|
-
}
|
|
43
|
-
return await response.json();
|
|
44
|
-
} catch (err) {
|
|
45
|
-
if (err instanceof Error) {
|
|
46
|
-
console.error('Error fetching priority fees:', err.message);
|
|
47
|
-
} else {
|
|
48
|
-
console.error('Unknown error fetching priority fees:', err);
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
return [];
|
|
53
|
-
}
|
package/src/pyth/constants.ts
DELETED
|
@@ -1,9 +0,0 @@
|
|
|
1
|
-
import { PublicKey } from '@solana/web3.js';
|
|
2
|
-
|
|
3
|
-
export const DEFAULT_WORMHOLE_PROGRAM_ID = new PublicKey(
|
|
4
|
-
'HDwcJBJXjL9FpJ7UBsYBtaDjsBUhuLCUYoz3zr8SWWaQ'
|
|
5
|
-
);
|
|
6
|
-
|
|
7
|
-
export const DEFAULT_RECEIVER_PROGRAM_ID = new PublicKey(
|
|
8
|
-
'rec5EKMGg6MxZYaMdyBfgwp4d5rB9T1VQH5pJv5LtFJ'
|
|
9
|
-
);
|
package/src/pyth/index.ts
DELETED
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
export {
|
|
2
|
-
type WormholeCoreBridgeSolana,
|
|
3
|
-
WORMHOLE_CORE_BRIDGE_SOLANA_IDL,
|
|
4
|
-
type PythSolanaReceiver,
|
|
5
|
-
type PriceUpdateAccount,
|
|
6
|
-
} from './types';
|
|
7
|
-
export {
|
|
8
|
-
DEFAULT_WORMHOLE_PROGRAM_ID,
|
|
9
|
-
DEFAULT_RECEIVER_PROGRAM_ID,
|
|
10
|
-
} from './constants';
|
|
11
|
-
export { getGuardianSetPda } from './utils';
|
|
12
|
-
export {
|
|
13
|
-
PythLazerSubscriber,
|
|
14
|
-
type PythLazerPriceFeedArray,
|
|
15
|
-
} from './pythLazerSubscriber';
|