jupiter

package
v0.1.4 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jul 20, 2026 License: Apache-2.0 Imports: 13 Imported by: 0

Documentation

Index

Constants

This section is empty.

Variables

View Source
var (
	RateLimitFree = dex.RateLimit{QPS: 4, Burst: 8}
	RateLimitPro  = dex.RateLimit{QPS: 30, Burst: 60}
)

Functions

This section is empty.

Types

type BlockhashWithMetadata

type BlockhashWithMetadata struct {
	Blockhash            []int  `json:"blockhash"`
	LastValidBlockHeight uint64 `json:"lastValidBlockHeight"`
}

BlockhashWithMetadata mirrors Jupiter's response field; blockhash arrives as a JSON array of 32 integers, not a base58 string, so we decode through []int and expose Bytes() for the tx builder.

func (*BlockhashWithMetadata) Bytes

func (b *BlockhashWithMetadata) Bytes() [32]byte

type Candle

type Candle struct {
	Time   int64   `json:"time"` // unix seconds
	Open   float64 `json:"open"`
	High   float64 `json:"high"`
	Low    float64 `json:"low"`
	Close  float64 `json:"close"`
	Volume float64 `json:"volume"`
}

type ChartReq

type ChartReq struct {
	Mint     string
	Interval string // 1_MINUTE / 5_MINUTE / 15_MINUTE / 30_MINUTE / 1_HOUR / 4_HOUR / 1_DAY / 1_WEEK
	ToMs     int64  // unix ms; required upstream
	Candles  int
	Type     string // price | mcap (default price)
}

type ChartsRes

type ChartsRes struct {
	Candles []Candle `json:"candles"`
}

type Client

type Client struct {
	// contains filtered or unexported fields
}

func NewClient

func NewClient(token string, opts ...ClientOption) *Client

NewClient constructs a Jupiter client with the free-tier rate limit as the default. Pass WithRateLimit(jupiter.RateLimitPro) if you're using a paid api-key that raises the ceiling. Additional options (WithRPC, WithFeeAccount) can be layered on for the fee-payer / gasless path.

func NewClientWithOptions

func NewClientWithOptions(rpcURL, feeAccount, token string, opts ...ClientOption) *Client

NewClientWithOptions is the legacy 3-positional signature; kept backward-compatible because existing callers pass rpcURL / feeAccount as fixed strings. Prefer NewClient + WithRPC / WithFeeAccount for new code.

func (*Client) Charts

func (c *Client) Charts(ctx context.Context, req *ChartReq) (*ChartsRes, error)

https://datapi.jup.ag/v2/charts/{mint}?interval=&to=&candles=&type=&quote=usd `to` is required upstream; if not set we use now. quote is fixed to usd (the only value the upstream accepts).

func (*Client) Holders

func (c *Client) Holders(ctx context.Context, mint string) (*HoldersRes, error)

https://datapi.jup.ag/v1/holders/{mint} Returns top 100 holders sorted by amount desc, plus PnL data for holders that have on-chain trade history. limit/offset query params are ignored upstream so we don't expose them.

func (*Client) Quote

func (*Client) QuoteRaw

func (c *Client) QuoteRaw(ctx context.Context, in *dexmodel.DexQuoteIn) (*QuoteRes, *QuoteReq, error)

QuoteRaw exposes the unaggregated /swap/v1/quote response and the input QuoteReq so TradeService's server-fee-payer path can feed it into SwapInstructions without going through the full Quote()+buildSwap() pipeline (which would build a tx with the user as fee payer).

func (*Client) QuoteUltra

func (c *Client) QuoteUltra(ctx context.Context, in *dexmodel.DexQuoteIn) (*dexmodel.DexQuoteOut, error)

QuoteUltra wraps UltraOrder + the gasless conversion so TradeService only sees DexQuoteOut. Returns (nil, nil) when Ultra succeeds but the route isn't jupiterz — caller treats that as "fall back to regular".

func (*Client) Status

func (*Client) SwapInstructions

func (c *Client) SwapInstructions(ctx context.Context, req *SwapInstructionsReq) (*SwapInstructionsRes, error)

SwapInstructions fetches the raw instruction list for a previously-built quote. Caller assembles its own v0 versioned tx — typically with a custom fee payer — instead of accepting Jupiter's default tx where the user is fee payer.

func (*Client) UltraExecute

func (c *Client) UltraExecute(ctx context.Context, req *UltraExecuteReq) (*UltraExecuteRes, error)

UltraExecute submits a signed tx through Ultra's relayer. Only valid after UltraOrder returned router="jupiterz"; for metis routes we go through Solana RPC directly.

func (*Client) UltraOrder

func (c *Client) UltraOrder(ctx context.Context, req *UltraOrderReq) (*UltraOrderRes, error)

UltraOrder fetches a quote from Ultra. Caller inspects res.Router to decide the execution path: "jupiterz" means res.Transaction is ready to be signed and submitted via UltraExecute; "metis" means we still need to assemble the tx ourselves (via swap-instructions) with our own fee payer.

type ClientOption

type ClientOption func(*clientConfig)

func WithDataBase added in v0.1.4

func WithDataBase(url string) ClientOption

func WithFeeAccount

func WithFeeAccount(addr string) ClientOption

func WithRPC

func WithRPC(url string) ClientOption

func WithRateLimit

func WithRateLimit(r dex.RateLimit) ClientOption

func WithSwapBase added in v0.1.4

func WithSwapBase(url string) ClientOption

func WithUltraBase added in v0.1.4

func WithUltraBase(url string) ClientOption

type Holder

type Holder struct {
	Address           string             `json:"address"`
	Amount            float64            `json:"amount"`
	SolBalance        string             `json:"solBalance"`
	SolBalanceDisplay float64            `json:"solBalanceDisplay"`
	AddressInfo       *HolderAddressInfo `json:"addressInfo,omitempty"`
	Tags              []HolderTag        `json:"tags"`
}

type HolderAddressInfo

type HolderAddressInfo struct {
	FundingAddress   string  `json:"fundingAddress"`
	FundingAmount    float64 `json:"fundingAmount"`
	FundingTx        string  `json:"fundingTx"`
	FundingBlockTime string  `json:"fundingBlockTime"`
	FundingSlot      int64   `json:"fundingSlot"`
}

type HolderPnl

type HolderPnl struct {
	RealizedPnl                   float64 `json:"realizedPnl"`
	RealizedPnlNative             float64 `json:"realizedPnlNative"`
	UnrealizedPnl                 float64 `json:"unrealizedPnl"`
	UnrealizedPnlNative           float64 `json:"unrealizedPnlNative"`
	TotalPnl                      float64 `json:"totalPnl"`
	TotalPnlNative                float64 `json:"totalPnlNative"`
	TotalBuys                     int     `json:"totalBuys"`
	TotalSells                    int     `json:"totalSells"`
	BoughtAmount                  float64 `json:"boughtAmount"`
	BoughtValue                   float64 `json:"boughtValue"`
	BoughtValueNative             float64 `json:"boughtValueNative"`
	SoldAmount                    float64 `json:"soldAmount"`
	SoldValue                     float64 `json:"soldValue"`
	SoldValueNative               float64 `json:"soldValueNative"`
	RealizedPnlPercentage         float64 `json:"realizedPnlPercentage"`
	RealizedPnlPercentageNative   float64 `json:"realizedPnlPercentageNative"`
	UnrealizedPnlPercentage       float64 `json:"unrealizedPnlPercentage"`
	UnrealizedPnlPercentageNative float64 `json:"unrealizedPnlPercentageNative"`
	TotalPnlPercentage            float64 `json:"totalPnlPercentage"`
	TotalPnlPercentageNative      float64 `json:"totalPnlPercentageNative"`
}

type HolderTag

type HolderTag struct {
	ID   string `json:"id"`
	Name string `json:"name"`
}

type HoldersRes

type HoldersRes struct {
	Holders   []Holder              `json:"holders"`
	Count     int                   `json:"count"`
	HolderPnl map[string]*HolderPnl `json:"holderPnl"`
}

type InstructionAcct

type InstructionAcct struct {
	Pubkey     string `json:"pubkey"`
	IsSigner   bool   `json:"isSigner"`
	IsWritable bool   `json:"isWritable"`
}

type InstructionDTO

type InstructionDTO struct {
	ProgramID string            `json:"programId"`
	Accounts  []InstructionAcct `json:"accounts"`
	Data      string            `json:"data"` // base64
}

type OndoMarketInfo

type OndoMarketInfo struct {
	IsOpen    bool   `json:"isOpen"`
	NextOpen  string `json:"nextOpen"`
	NextClose string `json:"nextClose"`
}

type OndoStatus

type OndoStatus struct {
	PauseInfo  json.RawMessage `json:"pauseInfo,omitempty"`
	MarketInfo OndoMarketInfo  `json:"marketInfo"`
}

type PlatformFee

type PlatformFee struct {
	Amount string `json:"amount"`
	FeeBps int    `json:"feeBps"`
}

type QuoteReq

type QuoteReq struct {
	InputMint      string
	OutputMint     string
	Amount         string
	SlippageBps    string
	PlatformFeeBps string
	UserPublicKey  string
}

type QuoteRes

type QuoteRes struct {
	ErrorCode            string          `json:"errorCode,omitempty"`
	ErrorMsg             string          `json:"error,omitempty"`
	InputMint            string          `json:"inputMint"`
	OutputMint           string          `json:"outputMint"`
	InAmount             string          `json:"inAmount"`
	OutAmount            string          `json:"outAmount"`
	OtherAmountThreshold string          `json:"otherAmountThreshold"`
	SwapMode             string          `json:"swapMode"`
	SlippageBps          int             `json:"slippageBps"`
	PlatformFee          *PlatformFee    `json:"platformFee,omitempty"`
	PriceImpactPct       string          `json:"priceImpactPct"`
	RoutePlan            []RoutePlanStep `json:"routePlan"`
	ContextSlot          int64           `json:"contextSlot"`
	TimeTaken            float64         `json:"timeTaken"`
}

type RoutePlanStep

type RoutePlanStep struct {
	SwapInfo struct {
		AmmKey     string `json:"ammKey"`
		Label      string `json:"label"`
		InputMint  string `json:"inputMint"`
		OutputMint string `json:"outputMint"`
		InAmount   string `json:"inAmount"`
		OutAmount  string `json:"outAmount"`
		FeeAmount  string `json:"feeAmount"`
		FeeMint    string `json:"feeMint"`
	} `json:"swapInfo"`
	Percent int `json:"percent"`
}

type SignatureStatusRes

type SignatureStatusRes struct {
	Result struct {
		Value []*SignatureStatusValue `json:"value"`
	} `json:"result"`
	Error *struct {
		Code    int    `json:"code"`
		Message string `json:"message"`
	} `json:"error,omitempty"`
}

type SignatureStatusValue

type SignatureStatusValue struct {
	Slot               int64       `json:"slot"`
	Confirmations      *int64      `json:"confirmations"`
	ConfirmationStatus string      `json:"confirmationStatus"`
	Err                interface{} `json:"err"`
}

type StockAsset

type StockAsset struct {
	ID              string     `json:"id"`
	Name            string     `json:"name"`
	Symbol          string     `json:"symbol"`
	Icon            string     `json:"icon"`
	Decimals        int        `json:"decimals"`
	Website         string     `json:"website"`
	Dev             string     `json:"dev"`
	CircSupply      float64    `json:"circSupply"`
	TotalSupply     float64    `json:"totalSupply"`
	TokenProgram    string     `json:"tokenProgram"`
	MintAuthority   string     `json:"mintAuthority"`
	FreezeAuthority string     `json:"freezeAuthority"`
	FirstPool       StockPool  `json:"firstPool"`
	HolderCount     int        `json:"holderCount"`
	Audit           StockAudit `json:"audit"`
	StockData       StockData  `json:"stockData"`
	OrganicScore    float64    `json:"organicScore"`
	OrganicLabel    string     `json:"organicScoreLabel"`
	CtLikes         int        `json:"ctLikes"`
	IsVerified      bool       `json:"isVerified"`
	Tags            []string   `json:"tags"`
	CreatedAt       string     `json:"createdAt"`
	FDV             float64    `json:"fdv"`
	MCap            float64    `json:"mcap"`
	UsdPrice        float64    `json:"usdPrice"`
	PriceBlockID    int64      `json:"priceBlockId"`
	Liquidity       float64    `json:"liquidity"`
	Stats5m         StockStats `json:"stats5m"`
	Stats1h         StockStats `json:"stats1h"`
	Stats6h         StockStats `json:"stats6h"`
	Stats24h        StockStats `json:"stats24h"`
	Stats7d         StockStats `json:"stats7d"`
	Stats30d        StockStats `json:"stats30d"`
	Fees            float64    `json:"fees"`
	UpdatedAt       string     `json:"updatedAt"`
}

type StockAudit

type StockAudit struct {
	TopHoldersPercentage    float64           `json:"topHoldersPercentage"`
	DevMints                int               `json:"devMints"`
	PermanentControlEnabled bool              `json:"permanentControlEnabled"`
	MutableFees             bool              `json:"mutableFees"`
	BotHoldersCount         int               `json:"botHoldersCount"`
	BotHoldersPercentage    float64           `json:"botHoldersPercentage"`
	DevFundedAt             string            `json:"devFundedAt"`
	BundlerStats            StockBundlerStats `json:"bundlerStats"`
}

type StockBundlerStats

type StockBundlerStats struct {
	TotalBundles   int     `json:"totalBundles"`
	TotalNativeVol float64 `json:"totalNativeVol"`
	HoldingPctATH  float64 `json:"holdingPctATH"`
}

type StockData

type StockData struct {
	ID        string  `json:"id"`
	Price     float64 `json:"price"`
	MCap      float64 `json:"mcap"`
	UpdatedAt string  `json:"updatedAt"`
}

type StockPool

type StockPool struct {
	ID        string `json:"id"`
	CreatedAt string `json:"createdAt"`
}

type StockStats

type StockStats struct {
	PriceChange       float64 `json:"priceChange"`
	HolderChange      float64 `json:"holderChange"`
	LiquidityChange   float64 `json:"liquidityChange"`
	VolumeChange      float64 `json:"volumeChange"`
	BuyVolume         float64 `json:"buyVolume"`
	SellVolume        float64 `json:"sellVolume"`
	BuyOrganicVolume  float64 `json:"buyOrganicVolume"`
	SellOrganicVolume float64 `json:"sellOrganicVolume"`
	NumBuys           int     `json:"numBuys"`
	NumSells          int     `json:"numSells"`
	NumTraders        int     `json:"numTraders"`
	NumOrganicBuyers  int     `json:"numOrganicBuyers"`
	NumNetBuyers      int     `json:"numNetBuyers"`
}

type StocksQuery

type StocksQuery struct {
	SortBy            string // e.g. "volume", "mcap", "liquidity"
	SortDir           string // "asc" or "desc"
	Limit             int
	Offset            int
	IncludeOndoStatus bool
}

type StocksRes

type StocksRes struct {
	Assets     []StockAsset `json:"assets"`
	Total      int          `json:"total"`
	Next       int          `json:"next"`
	OndoStatus *OndoStatus  `json:"ondoStatus,omitempty"`
}

type SwapInstructionsReq

type SwapInstructionsReq struct {
	UserPublicKey            string    `json:"userPublicKey"`
	QuoteResponse            *QuoteRes `json:"quoteResponse"`
	WrapAndUnwrapSol         bool      `json:"wrapAndUnwrapSol"`
	UseSharedAccounts        bool      `json:"useSharedAccounts"`
	FeeAccount               string    `json:"feeAccount,omitempty"`
	DynamicComputeUnitLimit  bool      `json:"dynamicComputeUnitLimit,omitempty"`
	SkipUserAccountsRpcCalls bool      `json:"skipUserAccountsRpcCalls,omitempty"`
}

SwapInstructionsReq feeds POST /swap/v1/swap-instructions. UserPublicKey is the account whose USDC moves, not the fee payer — we put our own wallet in the fee-payer slot when assembling the v0 tx.

type SwapInstructionsRes

type SwapInstructionsRes struct {
	TokenLedgerInstruction        *InstructionDTO       `json:"tokenLedgerInstruction"`
	ComputeBudgetInstructions     []InstructionDTO      `json:"computeBudgetInstructions"`
	SetupInstructions             []InstructionDTO      `json:"setupInstructions"`
	SwapInstruction               *InstructionDTO       `json:"swapInstruction"`
	CleanupInstruction            *InstructionDTO       `json:"cleanupInstruction"`
	AddressLookupTableAddresses   []string              `json:"addressLookupTableAddresses"`
	AddressesByLookupTableAddress map[string][]string   `json:"addressesByLookupTableAddress"`
	BlockhashWithMetadata         BlockhashWithMetadata `json:"blockhashWithMetadata"`
	PrioritizationFeeLamports     int64                 `json:"prioritizationFeeLamports"`
	ComputeUnitLimit              int64                 `json:"computeUnitLimit"`
	OtherInstructions             []InstructionDTO      `json:"otherInstructions"`
	SimulationError               json.RawMessage       `json:"simulationError"`
	ErrorCode                     string                `json:"errorCode,omitempty"`
	ErrorMessage                  string                `json:"error,omitempty"`
}

type SwapReq

type SwapReq struct {
	QuoteResponse           *QuoteRes `json:"quoteResponse"`
	UserPublicKey           string    `json:"userPublicKey"`
	WrapAndUnwrapSol        bool      `json:"wrapAndUnwrapSol"`
	DynamicComputeUnitLimit bool      `json:"dynamicComputeUnitLimit"`
	FeeAccount              string    `json:"feeAccount,omitempty"`
}

type SwapRes

type SwapRes struct {
	ErrorCode                 string `json:"errorCode,omitempty"`
	ErrorMsg                  string `json:"error,omitempty"`
	SwapTransaction           string `json:"swapTransaction"`
	LastValidBlockHeight      int64  `json:"lastValidBlockHeight"`
	PrioritizationFeeLamports int64  `json:"prioritizationFeeLamports"`
}

type UltraExecuteReq

type UltraExecuteReq struct {
	SignedTransaction string `json:"signedTransaction"`
	RequestID         string `json:"requestId"`
}

type UltraExecuteRes

type UltraExecuteRes struct {
	Status    string `json:"status"`
	Signature string `json:"signature"`
	Slot      uint64 `json:"slot"`
	Code      int    `json:"code"`
	Error     string `json:"error"`
}

type UltraOrderReq

type UltraOrderReq struct {
	InputMint   string
	OutputMint  string
	Amount      string
	Taker       string
	SlippageBps int // 0 == let Ultra pick dynamic slippage
}

UltraOrderReq builds the GET /ultra/v1/order query. Amount is in input mint's smallest unit; Taker is the user's wallet pubkey (base58).

type UltraOrderRes

type UltraOrderRes struct {
	Router  string `json:"router"`
	Gasless bool   `json:"gasless"`
	Mode    string `json:"mode"`

	InputMint            string `json:"inputMint"`
	OutputMint           string `json:"outputMint"`
	InAmount             string `json:"inAmount"`
	OutAmount            string `json:"outAmount"`
	OtherAmountThreshold string `json:"otherAmountThreshold"`
	SlippageBps          int    `json:"slippageBps"`
	PriceImpactPct       string `json:"priceImpactPct"`

	Taker     string `json:"taker"`
	RequestID string `json:"requestId"`

	SignatureFeePayer         string `json:"signatureFeePayer"`
	PrioritizationFeePayer    string `json:"prioritizationFeePayer"`
	RentFeePayer              string `json:"rentFeePayer"`
	SignatureFeeLamports      int64  `json:"signatureFeeLamports"`
	PrioritizationFeeLamports int64  `json:"prioritizationFeeLamports"`
	RentFeeLamports           int64  `json:"rentFeeLamports"`

	Transaction          string `json:"transaction"` // gasless path only
	LastValidBlockHeight uint64 `json:"lastValidBlockHeight"`

	ErrorCode    string `json:"errorCode,omitempty"`
	ErrorMessage string `json:"errorMessage,omitempty"`
}

UltraOrderRes mirrors /ultra/v1/order. Router distinguishes the RFQ gasless path ("jupiterz") from regular aggregator ("metis"); Gasless is the explicit boolean. Transaction is base64 versioned tx and is only populated on the gasless path — metis still requires us to fetch swap instructions and assemble the tx with our own fee payer.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL