Migration from 0.x
The 1.0 line (1.0.0) is a breaking migration to the current GalaChain DEX contract. Legacy names are removed; do not add compatibility fields to v2 DTOs.
From 1.2.x to 2.0.0: signing moved to @gala-chain/gala-core-sdk
The signing, transport, wallet-helper and base-error layer moved out of this
package into the peer package @gala-chain/gala-core-sdk. The DEX API, the write
protocol and the DTOs are unchanged. Install both packages
(npm install @gala-chain/gswap-sdk@next @gala-chain/gala-core-sdk@next: both are
release candidates under the next dist-tag); the peer range is >=1.0.0-rc.7 <2.
| 1.2.x | 2.0.0 |
|---|---|
import { PrivateKeySigner, GalaWalletSigner, BrowserWalletSigner, serialize, signNative, ... } from '@gala-chain/gswap-sdk' | The same names from @gala-chain/gala-core-sdk (no re-export from this package) |
@gala-chain/gswap-sdk/wallet | @gala-chain/gala-core-sdk/wallet |
isGSwapErrorLike, GSwapErrorShape, GSWAP_ERROR_PHASES, GSwapErrorPhase, GSwapErrorContext, renderGSwapErrorTemplate | isGalaErrorLike, GalaErrorShape, GALA_ERROR_PHASES, GalaErrorPhase, GalaErrorContext, renderGalaErrorTemplate |
Error brand Symbol.for('@gala-chain/gswap-sdk/error') | Symbol.for('@gala-chain/gala-core-sdk/error') |
error instanceof GSwapSDKError | isGSwapError(error) or core's isGalaError(error): a signer or transport error is a plain GalaSDKError |
gswapErrorTemplates held every code | DEX codes only; merge with core's galaErrorTemplates |
See core's Migrating from gswap-sdk 1.x for the full old-path to new-path table.
From 1.1.x to 1.2.0 (release candidates on the rc tag)
The 1.2.0 line changes how errors reach your code. The write protocol and DTOs are unchanged.
| 1.1.x | 1.2.0-rc |
|---|---|
new GSwapSDKError(message, code, details), error.details, userMessage, chainMessage | new GSwapSDKError(code, params, context); error.params (flat primitives), typed status, url, uniqueKey, requestTransactionId, applyTransactionId, blockNumber, retryAfterMs, body, bodyText, cause. error.message is English for logs only; branch on code. |
A chain ErrorKey as error.code | CHAIN_REJECTED with params.errorKey and params.serverMessage |
VALIDATION_ERROR / INVALID_GATEWAY_RESPONSE with details.type | One code per fault (INVALID_FEE, NON_CANONICAL_PAIR, GATEWAY_DATA_MISSING, ...) |
| Retry and outcome rules kept in each app | classifyFailure(error), isNoMarket, mayHaveBeenQueued, pendingSwapFateFor |
Signing through @gala-chain/api | The SDK's own primitives on @noble/curves / @noble/hashes; @gala-chain/api is a devDependency only |
GalaWalletSigner fell back to personal-sign on a wallet that rejected native | No fallback; { scheme: 'personal-sign' } is explicit and needs a wallet build with the fix |
See Error Handling and Signing and Identity.
Changes between 1.0.0-rc.3 and 1.0.0-rc.4
A class key carries no symbol. Collection and symbol disagree for many tokens (GBNB's symbol is
BNB, every launchpad token shares the collection Token, and some real collections contain the
$ delimiter, e.g. $GMUSIC), so the SDK never derives one from the other.
createPoolfor a token with no registered trading symbol now needs one. Passtoken0Symbol/token1Symbol(ASCII letters and digits); without it the call throwsTOKEN_SYMBOL_NOT_REGISTEREDinstead of proposing the raw collection (which the bouncer rejects for any collection containing_or$, and always for launchpad tokens). A symbol that disagrees with the one already registered for that class is rejected. The CLI'screate_pooltakes the two optional symbol arguments.- Class keys parse from the right. The last three segments are category, type and
additionalKey; everything before them is the collection, so
$GMUSIC$Unit$none$noneresolves instead of failing as a five-part key. - Docs and examples no longer treat
collectionas the symbol (full_dexpasses full class keys and carries an explicitsymbolper token).
Changes between 1.0.0-rc.2 and 1.0.0-rc.3
BrowserWalletSignerpersonal-sign now signs the bare serialized DTO and sends the EIP-191 header (\u0019Ethereum Signed Message:\n<byte length>) as the DTO'sprefix. The previous recipe embeddedprefixin the signed message, which the chain recovers to an address nobody holds, so a personal-signCreatePoolcould execute under a phantom creator; the swap backend now rejects that shape. No caller changes are needed; re-sign nothing.GalaWalletSigner's personal-sign scheme carries the same header value (the wallet prepends it before hashing).
Changes between 1.0.0-rc.1 and 1.0.0-rc.2
Swaps are queued. The synchronous Trade method was removed from the contract
and from this SDK, with no fallback.
| rc.1 | rc.2 |
|---|---|
swaps.swap() signed and submitted Trade; the executed result came back inline | signs and submits RequestTrade; the gateway acknowledges with mode: 'queued' and result === undefined |
SubmittedTransaction.mode was always 'sync' | 'sync' for liquidity writes, 'queued' for swaps |
confirm() polled the indexed transaction and returned IndexedTransaction | reads apply-results and returns AppliedTrade (apply transactionId, blockNumber, requestTransactionId, executed result), or throws the chain's rejection (in 1.1.x its ErrorKey was error.code; since 1.2.0-rc.3 it is CHAIN_REJECTED with params.errorKey) |
| — | swaps.confirmSwap(uniqueKey) resolves a swap from the persisted key alone |
TradeDTO | RequestTradeDTO (same fields) |
ConfirmOptions had timeoutMs, pollIntervalMs | adds initialDelayMs (default 3 s for swaps, 0 for liquidity writes) |
CONFIRMATION_TIMEOUT meant "not indexed yet" | means the outcome is unknown: confirm the same key again, never resubmit |
gateway.submit('Trade', …) | refused locally with METHOD_NOT_SUPPORTED |
API replacements
| 0.x | v2 replacement |
|---|---|
Bundler | Chain Gateway writes through GSwap |
Events / EventSocketClient | No socket; call SubmittedTransaction.confirm() |
PendingTransaction | SubmittedTransaction |
TxWaiter | SubmittedTransaction.confirm() |
PendingTransaction.wait() | SubmittedTransaction.confirm() |
TransactionPendingResponse | AppliedTrade returned by confirm() for a queued swap |
stringsInstructions | Removed; the gateway derives chain references |
| bundle IDs | uniqueKey |
transactionId as the only correlation key | uniqueKey; request transactionId may be null |
GSwap.events.connectEventSocket() | Removed |
GSwap.swap(...) | gSwap.swaps.swap(tokenIn, tokenOut, fee, params) |
pools.getPoolData(...) | pools.getPool(...) |
positions.getPositionById(...) | positions.getPosition({ t0, t1, fee, owner, tickLower, tickUpper }) |
DTO field replacements
| Removed field or shape | v2 shape |
|---|---|
Class-key object token0 / token1 in writes | Trading-symbol token0 / token1; SDK accepts a symbol or class key as input |
amount | One of sell0Qty, sell1Qty, buy0Qty, buy1Qty |
zeroForOne | Derived from token ordering and exact-in/exact-out side |
sqrtPriceLimit | Removed; use quote slippage fields |
positionId | Position identity: symbols, fee, owner, and tick range |
amount0Desired, amount1Desired | Exactly one depositQuantityToken0 or depositQuantityToken1 |
amount0Min, amount1Min | amountOutMinimum for trades, or estimate before a liquidity write |
| Partial collect amounts | Removed; collectPositionFees sweeps everything |
| Partial remove percentage | Optional withdrawalQuantityToken0 or withdrawalQuantityToken1; omit both to close |
CreatePool class-key token0 / token1 | token0Key / token1Key plus token0Symbol / token1Symbol |
FEE_TIER without zero | Fee tiers 0, 500, 3000, 10000 |
Transaction flow
Build a quote, choose the fee and slippage bound, submit through the SDK, then
persist uniqueKey and confirm. A queued swap acknowledgement has
mode: 'queued', no result, and a request transactionId when provided; the
applied outcome is returned by confirm().
const quote = await gSwap.quoting.quoteExactOutput('GALA', 'GUSDC', '50');
const tx = await gSwap.swaps.swap('GALA', 'GUSDC', quote.feeTier, {
exactOut: '50',
amountInMaximum: quote.amountIn,
});
await tx.confirm();
Signing migration
PrivateKeySigner remains native. GalaWalletSigner no longer signs EIP-712;
it uses native gala_signChainDto. The older-wallet personal-sign fallback was removed
(on released wallets it recovered a phantom signer); scheme: 'personal-sign' remains as an
explicit opt-in that requires a wallet build containing the fix.
Use BrowserWalletSigner for generic EIP-1193 wallets. See
Signing and Identity.