Skip to main content
If you’re currently using @sqds/grid v2.x, this guide will help you migrate to v3.0.0. The new version introduces improved error handling, camelCase field naming, new trading features, and better state management.

Overview of Breaking Changes

v3.0.0 introduces several breaking changes that improve the developer experience:
  • Error handling: Methods now throw GridError instead of returning {success, error} wrappers
  • camelCase naming: All response/request fields now use camelCase instead of snake_case
  • Response structure: All responses have a .data object containing the payload
  • New features: Account state management, trading smart transactions, and passkey accounts

Migration Steps

1

Update Package Version

Update your package.json and install v3.0.0:
npm install @sqds/grid@3.0.0
2

Update Error Handling Pattern

Replace all success checks with try/catch blocks. Methods now throw GridError on failure.Before (v2.x):
const response = await gridClient.createAccount({
  email: "user@example.com",
});

if (response.success) {
  console.log("Account created:", response.data.address);
} else {
  console.error("Error:", response.error);
}
After (v3.0.0):
import { GridClient, GridError } from '@sqds/grid';

try {
  const response = await gridClient.createAccount({
    email: "user@example.com",
  });
  console.log("Account created:", response.data.address);
} catch (error) {
  if (error instanceof GridError) {
    console.error("Error:", error.message);
    console.error("Code:", error.code);
    console.error("Status:", error.statusCode);
    console.error("Request ID:", error.lastResponse?.requestId);
  }
}
The GridError class provides structured error information including code, statusCode, details, and lastResponse for debugging.
3

Update Field Names to camelCase

All response and request fields now use camelCase instead of snake_case.Before (v2.x):
const auth = await gridClient.initAuth({ email: "user@example.com" });
if (auth.success) {
  console.log("OTP sent:", auth.data.otp_sent);
  console.log("Created:", auth.data.created_at);
  console.log("Expires:", auth.data.expires_at);
}

const account = await gridClient.getAccount(address);
if (account.success) {
  console.log("User ID:", account.data.grid_user_id);
  console.log("Time lock:", account.data.policies?.time_lock);
  console.log("Admin:", account.data.policies?.admin_address);
}
After (v3.0.0):
try {
  const auth = await gridClient.initAuth({ email: "user@example.com" });
  console.log("OTP sent:", auth.data.otpSent);
  console.log("Created:", auth.data.createdAt);
  console.log("Expires:", auth.data.expiresAt);

  const account = await gridClient.getAccount(address);
  console.log("User ID:", account.data.gridUserId);
  console.log("Time lock:", account.data.policies?.timeLock);
  console.log("Admin:", account.data.policies?.adminAddress);
} catch (error) {
  console.error("Failed:", error);
}
Complete field name mapping:
Old (snake_case)New (camelCase)
otp_sentotpSent
otp_idotpId
created_atcreatedAt
expires_atexpiresAt
grid_user_idgridUserId
time_locktimeLock
admin_addressadminAddress
transaction_signerstransactionSigners
spending_limit_signersspendingLimitSigners
transaction_signaturetransactionSignature
confirmed_atconfirmedAt
GridError field change:
// Before
error.status_code

// After
error.statusCode
4

Update Response Access Pattern

Responses now use BaseResponse<T> which wraps data in a .data property along with request metadata in .lastResponse.Before (v2.x):
const balances = await gridClient.getAccountBalances(address);
if (balances.success) {
  balances.data.tokens.forEach((token) => {
    console.log(`${token.symbol}: ${token.amount}`);
  });
}
After (v3.0.0):
try {
  const balances = await gridClient.getAccountBalances(address);

  balances.data.tokens.forEach((token) => {
    console.log(`${token.symbol}: ${token.amount}`);
  });

  console.log("Request ID:", balances.lastResponse?.requestId);
} catch (error) {
  console.error("Failed to fetch balances:", error);
}
The .data property contains your actual response payload. The .lastResponse property contains request metadata (requestId, statusCode, headers) useful for debugging and support.
5

Update Transaction Signing Flow

Update authentication data access to use camelCase.Before (v2.x):
const spendingLimit = await gridClient.createSpendingLimit(
  address,
  spendingLimitPayload
);

if (spendingLimit.success) {
  const signature = await gridClient.signAndSend({
    sessionSecrets,
    session: authResult.data.authentication,
    transactionPayload: spendingLimit.data,
    address,
  });
}
After (v3.0.0):
try {
  const spendingLimit = await gridClient.createSpendingLimit(
    address,
    spendingLimitPayload
  );

  const signature = await gridClient.signAndSend({
    sessionSecrets,
    session: authResult.data.authentication,
    transactionPayload: spendingLimit.data,
    address,
  });

  console.log("Transaction completed:", signature.data.transactionSignature);
} catch (error) {
  console.error("Transaction failed:", error);
}
6

Update Type References

Several response types have been updated. The main change is removing the old GridResponse<T> wrapper.Type updates:
// Old types (v2.x)
GridResponse<GetAccountResponse>
GridResponse<CreateAccountResponse>
GridResponse<AccountBalancesData>

// New types (v3.0.0) - use directly
GetAccountResponse
CreateAccountResponse
AccountBalancesResponse
Update your function signatures:
// Before
const handleAccount = async (): Promise<GridResponse<GetAccountResponse>> => {
  return await gridClient.getAccount(address);
};

// After
const handleAccount = async (): Promise<GetAccountResponse> => {
  return await gridClient.getAccount(address);
};
7

Verify All Changes

Run TypeScript compilation and your test suite:
npm run type-check
npm test
Common errors to look for:
  • Property 'success' does not exist - Update to try/catch
  • Property 'xxx_yyy' does not exist - Update to camelCase
  • Property 'status_code' does not exist on type 'GridError' - Use statusCode

Migration Checklist

  • Update package to v3.0.0
  • Replace all if (response.success) checks with try/catch blocks
  • Import and use GridError for error handling
  • Update all snake_case field accesses to camelCase (see table above)
  • Update error.status_code to error.statusCode
  • Update type declarations to remove GridResponse<T> wrapper
  • Test authentication flows (initAuth, completeAuth)
  • Test transaction creation and signing
  • Verify error handling catches GridError correctly
  • Run TypeScript compilation to catch any missed changes