Jupiter Swap API Client

repository·main·Indexed 41 days ago

https://github.com/jup-ag/jupiter-swap-api-client

A Rust client library for the Jupiter Swap API, designed to facilitate token swaps on the Solana blockchain. It provides the JupiterSwapApiClient for fetching quotes via `quote()`, executing swaps via `swap()`, and retrieving granular Solana instructions via `swap_instructions()`. The library includes support for custom API URLs, dynamic slippage reports, and transaction prioritization types such as Jito and ComputeBudget.

Tokens
5.6K
Snippets
19
Records
25
Agent score
53%

What's inside Jupiter Swap API Client

  1. Install the jup-swap-api-client crate

    main

    To use the jup-swap-api-client in your Rust project, add the crate directly from the GitHub repository to your Cargo.toml file.

    [dependencies]
    jupiter-swap-api-client = { git = "https://github.com/jup-ag/jupiter-swap-api-client.git", package = "jupiter-swap-api-client"}
  2. Configure custom API URLs via environment variables

    main

    If you are using self-hosted Jupiter APIs (such as a self-hosted V6 Swap API) or paid hosted APIs, you can redirect the client by setting the following environment variable:

    API_BASE_URL: The base URL for the hosted API (e.g., https://hosted.api).

    API_BASE_URL=https://hosted.api
  3. Set the SwapMode (ExactIn vs ExactOut)

    main

    The SwapMode enum defines the direction of the swap and which amount is treated as the fixed constraint:

    • ExactIn: The input amount is fixed; slippage occurs on the output amount. This is the default mode.
    • ExactOut: The output amount is fixed; slippage occurs on the input amount. Useful for payments where a specific amount must be received.
    use jupiter_swap_api_client::quote::SwapMode;
    
    let mode = SwapMode::ExactOut;
  4. Configure transaction priority and fees

    main

    When building a TransactionConfig, you can prioritize your transaction using either compute_unit_price_micro_lamports or prioritization_fee_lamports. These two fields are mutually exclusive.

    Compute Unit Price

    Use compute_unit_price_micro_lamports to set a specific price per compute unit.

    • MicroLamports(u64): A specific value in micro-lamports.
    • Auto: Automatically determines the price.

    Prioritization Fee

    Use prioritization_fee_lamports to pay an additional fee for the transaction. Options include:

    • AutoMultiplier(u32): Uses a multiplier for automatic fee calculation.
    • JitoTipLamports(u64): A specific tip amount for Jito.
    • PriorityLevelWithMaxLamports: Uses a predefined PriorityLevel (Medium, High, or VeryHigh) with a max_lamports cap. Setting global: true applies the fee globally.
    • Lamports(u64): A fixed amount of lamports.
    • Auto: Automatic fee calculation.
    • Disabled: No prioritization fee.
    // Example: Setting a high priority via Jito tip
    let config = TransactionConfig {
        prioritization_fee_lamports: Some(PrioritizationFeeLamports::JitoTipLamports(100000)),
        ..Default::default()
    };
    
    // Example: Setting a specific compute unit price
    let config = TransactionConfig {
        compute_unit_price_micro_lamports: Some(ComputeUnitPriceMicroLamports::MicroLamports(500)),
        ..Default::default()
    };
  5. Understand the RoutePlanWithMetadata data structure

    main

    A RoutePlanWithMetadata is a topologically sorted Directed Acyclic Graph (DAG) represented as a Vec<RoutePlanStep>. It is used for rendering swap routes and includes metadata for each step in the route. Each step defines a specific swap operation and the percentage of the total volume flowing through that specific leg of the route.

    pub type RoutePlanWithMetadata = Vec<RoutePlanStep>;
  6. Use the JupiterSwapApiClient to quote, swap, and get instructions

    main

    The JupiterSwapApiClient provides high-level methods to interact with the Jupiter Swap API. You initialize it with a base URL (e.g., https://quote-api.jup.ag/v6).

    Key methods:

    • quote(&QuoteRequest): Fetches a quote for a potential swap. Requires an amount, input_mint, output_mint, and slippage_bps.
    • swap(&SwapRequest): Executes a swap request, returning a transaction. Requires user_public_key, the quote_response, and a TransactionConfig.
    • swap_instructions(&SwapRequest): Retrieves swap instructions instead of a full transaction.
    use jupiter_swap_api_client::{
        quote::QuoteRequest, swap::SwapRequest, transaction_config::TransactionConfig,
        JupiterSwapApiClient,
    };
    use solana_sdk::pubkey::Pubkey;
    
    const USDC_MINT: Pubkey = pubkey!("EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v");
    const NATIVE_MINT: Pubkey = pubkey!("So11111111111111111111111111111111111111112");
    const TEST_WALLET: Pubkey = pubkey!("2AQdpHJ2JpcEgPiATUXjQxA8QmafFegfQwSLWSprPicm");
    
    #[tokio::main]
    async fn main() {
        let jupiter_swap_api_client = JupiterSwapApiClient::new("https://quote-api.jup.ag/v6");
    
        let quote_request = QuoteRequest {
            amount: 1_000_000,
            input_mint: USDC_MINT,
            output_mint: NATIVE_MINT,
            slippage_bps: 50,
            ..QuoteRequest::default()
        };
    
        // GET /quote
        let quote_response = jupiter_swap_api_client.quote(&quote_request).await.unwrap();
        println!("{quote_response:#?}");
    
        // POST /swap
        let swap_response = jupiter_swap_api_client
            .swap(&SwapRequest {
                user_public_key: TEST_WALLET,
                quote_response: quote_response.clone(),
                config: TransactionConfig::default(),
            })
            .await
            .unwrap();
    
        println!("Raw tx len: {}", swap_response.swap_transaction.len());
    
        // POST /swap-instructions
        let swap_instructions = jupiter_swap_api_client
            .swap_instructions(&SwapRequest {
                user_public_key: TEST_WALLET,
                quote_response,
                config: TransactionConfig::default(),
            })
            .await
            .unwrap();
        println!("{swap_instructions:#?}");
    }
  7. Handle the QuoteResponse

    main

    The QuoteResponse contains the results of a quote request, providing the necessary data to execute a swap.

    Key fields include:

    • in_amount / out_amount: The final expected input and output amounts.
    • other_amount_threshold: The threshold used for validation (e.g., minimum output for ExactIn).
    • price_impact_pct: The estimated percentage impact on the liquidity pool price.
    • route_plan: A RoutePlanWithMetadata object describing the sequence of swaps.
    • platform_fee: An optional PlatformFee object containing the amount and fee_bps collected.
    • swap_mode: The mode used for the calculation.
    • context_slot: The Solana slot at the time of quote generation.
    // Example of accessing response data
    println!("Expected output: {}", response.out_amount);
    println!("Price impact: {}%", response.price_impact_pct);
  8. Configure a QuoteRequest for swaps

    main

    To obtain a swap quote and route plan, construct a QuoteRequest. This structure defines the parameters for the routing engine, including token mints, amounts, slippage, and routing constraints.

    Key configuration options include:

    • input_mint / output_mint: The Pubkey of the tokens being swapped.
    • amount: The quantity of the input or output token (depending on swap_mode).
    • swap_mode: Determines if the input or output amount is fixed (ExactIn or ExactOut).
    • slippage_bps: Maximum allowed slippage in basis points (e.g., 50 for 0.5%).
    • dexes / excluded_dexes: Comma-separated strings of DEX labels to include or exclude.
    • only_direct_routes: If true, restricts routing to single-hop swaps.
    • platform_fee_bps: Optional fee to collect in basis points.
    • compute_auto_slippage: Enables dynamic slippage calculation.

    Note: QuoteRequest::default() provides a safe default slippage of 50 BPS.

    let request = QuoteRequest {
        input_mint: input_pubkey,
        output_mint: output_pubkey,
        amount: 1000000, // amount in atoms
        swap_mode: Some(SwapMode::ExactIn),
        slippage_bps: 50,
        ..Default::default()
    };
  9. Understand SwapInfo for multi-hop routes

    main

    When a swap involves multiple hops, the route_plan contains a sequence of SwapInfo objects. Each SwapInfo represents a single step in the route and includes:

    • amm_key: The Pubkey of the AMM pool or program.
    • label: The human-readable name of the DEX (e.g., "Raydium_V4").
    • input_mint / output_mint: The tokens involved in this specific step.
    • in_amount / out_amount: The estimated amounts for this step (in atoms).
    // Iterating through route steps
    for step in response.route_plan.steps {
        println!("Step via {}: {} -> {}", step.label, step.input_mint, step.output_mint);
    }