Skip to content

All 12 x/gamm messages with fields and a JSON example each: pool creation, join, exit, swaps, single-asset joins and exits, stableswap, IBC swap.

Every message is signed by sender. Amounts are integer strings in the coin's base unit. Native tokens appear as badgeslp:<collectionId>:<denom> alias denoms and are subject to the collection's approvals (see x/gamm). Type URLs use the proto package: /gamm.v1beta1.Msg<Name>, except pool creation which lives under /gamm.poolmodels.balancer. and /gamm.poolmodels.stableswap..

MessagePurpose
MsgCreateBalancerPoolCreate a weighted pool with initial liquidity
MsgJoinPoolDeposit all assets proportionally for LP shares
MsgExitPoolBurn LP shares for all assets proportionally
MsgSwapExactAmountInSwap an exact input for at least a minimum output
MsgSwapExactAmountOutSwap at most a maximum input for an exact output
MsgSwapExactAmountInWithIBCTransferSwap, then send the output over IBC
MsgJoinSwapExternAmountInSingle-asset join with an exact token amount
MsgJoinSwapShareAmountOutSingle-asset join for an exact share amount
MsgExitSwapShareAmountInExit an exact share amount into one asset
MsgExitSwapExternAmountOutExit into an exact single-asset amount
MsgCreateStableswapPoolCreate a stableswap pool
MsgStableSwapAdjustScalingFactorsAdjust a stableswap pool's scaling factors

Ask your agent:

text
Swap 1 BADGE for badgeslp:64:utoken through pool 1 with 1% slippage and show me the transaction before you sign it.

The bb swap estimate ubadge badgeslp:64:utoken 1000000 --slippage 1 command and the liquidity-pools skill produce the MsgSwapExactAmountIn on this page.

MsgCreateBalancerPool

Creates a balancer pool. The pool ID is assigned at execution and returned in the response. The creator supplies the initial liquidity and sets the fees and weights; a dedicated module account is created for the pool.

json
{
    "@type": "/gamm.poolmodels.balancer.MsgCreateBalancerPool",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_params": {
        "swap_fee": "0.003000000000000000",
        "exit_fee": "0.000000000000000000"
    },
    "pool_assets": [
        {
            "token": { "denom": "ubadge", "amount": "1000000" },
            "weight": "50"
        },
        {
            "token": { "denom": "badgeslp:21:utoken", "amount": "5000000" },
            "weight": "50"
        }
    ]
}
proto
message MsgCreateBalancerPool {
  option (amino.name) = "gamm/CreateBalancerPool";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  gamm.poolmodels.balancer.PoolParams pool_params = 2;
  repeated gamm.poolmodels.balancer.PoolAsset pool_assets = 3;
}

// Returns the poolID
message MsgCreateBalancerPoolResponse {
  uint64 pool_id = 1;
}
FieldTypeRequiredDescription
senderstringyesPool creator; funds the initial liquidity
pool_params.swap_feeLegacyDec stringyesFee taken on each swap, for example 0.003 for 0.3%. Some serializers render this as an 18-decimal integer string such as 3000000000000000.
pool_params.exit_feeLegacyDec stringyesFee taken on exit
pool_assets[].tokenCoinyesDenom and initial amount
pool_assets[].weightInt stringyesRelative weight of the asset

Behavior: pool creation fails when any native asset's collection sets the disablePoolCreation invariant. There is no pool creation fee. The response pool_id is also emitted in transaction events.

MsgJoinPool

Joins a pool by depositing every asset in the current pool ratio. LP shares are minted to the sender. Internally this is "join pool, no swap".

json
{
    "@type": "/gamm.v1beta1.MsgJoinPool",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_id": "1",
    "share_out_amount": "1000000",
    "token_in_maxs": [
        { "denom": "badgeslp:64:utoken", "amount": "10" },
        { "denom": "ubadge", "amount": "160000000" }
    ]
}
proto
message MsgJoinPool {
  option (amino.name) = "gamm/JoinPool";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  uint64 pool_id = 2;
  string share_out_amount = 3;                       // math.Int
  repeated cosmos.base.v1beta1.Coin token_in_maxs = 4;
}

message MsgJoinPoolResponse {
  string share_out_amount = 1;                       // math.Int
  repeated cosmos.base.v1beta1.Coin token_in = 2;
}
FieldTypeRequiredDescription
senderstringyesDepositor
pool_iduint64yesTarget pool
share_out_amountInt stringyesExact LP shares to receive
token_in_maxsCoin[]yesSlippage cap: the most of each asset the join may consume

Behavior: tokens must be provided in the pool's current proportions; otherwise the transaction fails. Shares are minted to sender, pool liquidity rises, and the sender starts earning swap fees. Shares can be held, staked in yield programs, or used for governance where a pool supports it.

MsgExitPool

Burns LP shares and returns every underlying asset in proportion to the share. The sender cannot pick which assets to receive.

json
{
    "@type": "/gamm.v1beta1.MsgExitPool",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_id": "1",
    "share_in_amount": "100000",
    "token_out_mins": [
        { "denom": "badgeslp:64:utoken", "amount": "1" },
        { "denom": "ubadge", "amount": "15000000" }
    ]
}
proto
message MsgExitPool {
  option (amino.name) = "gamm/ExitPool";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  uint64 pool_id = 2;
  string share_in_amount = 3;                        // math.Int
  repeated cosmos.base.v1beta1.Coin token_out_mins = 4;
}

message MsgExitPoolResponse {
  repeated cosmos.base.v1beta1.Coin token_out = 1;
}
FieldTypeRequiredDescription
senderstringyesShare holder
pool_iduint64yesPool to exit
share_in_amountInt stringyesLP shares to burn
token_out_minsCoin[]yesSlippage floor: the least of each asset that must come back

Behavior: shares are burned, the exit fee (if the pool has one) is deducted, and the assets are returned proportionally. A native asset's collection approvals must allow the transfer from the pool to the sender.

MsgSwapExactAmountIn

Swaps an exact token_in for at least token_out_min_amount of the last route's output denom.

json
{
    "@type": "/gamm.v1beta1.MsgSwapExactAmountIn",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "routes": [
        { "pool_id": "1", "token_out_denom": "badgeslp:64:utoken" }
    ],
    "token_in": { "denom": "ubadge", "amount": "1000000000" },
    "token_out_min_amount": "60",
    "affiliates": [
        { "basis_points_fee": "10", "address": "bb1zc268nctj8xwslgw7q22cahs6k4y048agr6fvf" }
    ]
}
proto
message MsgSwapExactAmountIn {
  option (amino.name) = "gamm/SwapExactAmountIn";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  repeated poolmanager.v1beta1.SwapAmountInRoute routes = 2;
  cosmos.base.v1beta1.Coin token_in = 3;
  string token_out_min_amount = 4;                   // math.Int
  repeated poolmanager.v1beta1.Affiliate affiliates = 5;
}

message MsgSwapExactAmountInResponse {
  string token_out_amount = 1;                       // math.Int
}

message Affiliate {
  string basis_points_fee = 1;
  string address = 2;
}
FieldTypeRequiredDescription
senderstringyesTrader
routesSwapAmountInRoute[]yesOrdered hops; each names a pool_id and token_out_denom
token_inCoinyesExact input
token_out_min_amountInt stringyesSlippage floor on the final output
affiliatesAffiliate[]noFee recipients paid from the swap output

Behavior: multi-hop swaps run through each pool in sequence. Each pool's swap fee is deducted from the input before the swap. Price impact depends on pool liquidity. Affiliate fees are optional, given in basis points (1 basis point = 0.01%, 100 = 1%), computed on the output, and several affiliates may be listed. With an output of 1,000,000 and one affiliate at 10 basis points, the affiliate receives 1,000 and the sender 999,000.

MsgSwapExactAmountOut

Swaps up to token_in_max_amount of the first route's input denom for exactly token_out.

json
{
    "@type": "/gamm.v1beta1.MsgSwapExactAmountOut",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "routes": [
        { "pool_id": "1", "token_in_denom": "ubadge" }
    ],
    "token_in_max_amount": "2000000000",
    "token_out": { "denom": "badgeslp:64:utoken", "amount": "1" }
}
proto
message MsgSwapExactAmountOut {
  option (amino.name) = "gamm/SwapExactAmountOut";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  repeated poolmanager.v1beta1.SwapAmountOutRoute routes = 2;
  string token_in_max_amount = 3;                    // math.Int
  cosmos.base.v1beta1.Coin token_out = 4;
}

message MsgSwapExactAmountOutResponse {
  string token_in_amount = 1;                        // math.Int
}
FieldTypeRequiredDescription
senderstringyesTrader
routesSwapAmountOutRoute[]yesOrdered hops; each names a pool_id and token_in_denom
token_in_max_amountInt stringyesSlippage cap on the input
token_outCoinyesExact output

Behavior: the response reports the input actually spent. No affiliate field exists on this message. Use it when the output amount matters more than the input, for example buying exactly one token.

MsgSwapExactAmountInWithIBCTransfer

Runs MsgSwapExactAmountIn, then sends the output to another chain over IBC in the same transaction. If any step fails, everything is rolled back.

json
{
    "@type": "/gamm.v1beta1.MsgSwapExactAmountInWithIBCTransfer",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "routes": [
        { "pool_id": "1", "token_out_denom": "ubadge" },
        { "pool_id": "4", "token_out_denom": "ibc/A4DB47A9D3CF9A068D454513891B526702455D3EF08FB9EB558C561F9DC2B701" }
    ],
    "token_in": { "denom": "badgeslp:64:utoken", "amount": "10" },
    "token_out_min_amount": "900000",
    "ibc_transfer_info": {
        "source_channel": "channel-3",
        "receiver": "cosmos1py4mfpg6uf59qkyzg0nmau322c5873ee8df8qg",
        "memo": "",
        "timeout_timestamp": "1788825600000000000"
    },
    "affiliates": [
        { "basis_points_fee": "10", "address": "bb1zc268nctj8xwslgw7q22cahs6k4y048agr6fvf" }
    ]
}
ts
export interface iIBCTransferInfo<T extends NumberType> {
    sourceChannel: string;
    receiver: string;
    memo: string;
    timeoutTimestamp: T;
}

export interface iMsgSwapExactAmountInWithIBCTransfer<T extends NumberType> {
    sender: string;
    routes: iSwapAmountInRoute<T>[];
    tokenIn: iCosmosCoin<T>;
    tokenOutMinAmount: T;
    ibcTransferInfo: iIBCTransferInfo<T>;
    affiliates?: iAffiliate[];
}

export interface iAffiliate {
    basisPointsFee: string;
    address: string;
}
FieldTypeRequiredDescription
senderstringyesTrader and IBC sender
routesSwapAmountInRoute[]yesSwap hops, executed in order before the transfer
token_inCoinyesExact input
token_out_min_amountInt stringyesSlippage floor
ibc_transfer_info.source_channelstringyesIBC channel to send through
ibc_transfer_info.receiverstringyesDestination chain address
ibc_transfer_info.memostringnoMemo attached to the IBC transfer
ibc_transfer_info.timeout_timestampuint64yesNanosecond timestamp after which the IBC transfer times out
affiliatesAffiliate[]noFee recipients, paid from the output before the IBC transfer

Behavior, in order: swap through the routes, check the minimum output, deduct affiliate fees (on the output, before transfer), send the remainder over IBC. Each pool's swap fee comes off the input; the IBC transfer fee comes off the output. With an output of 1,000,000 and an affiliate at 10 basis points, 1,000 goes to the affiliate and 999,000 is transferred. The output denom must be an x/bank coin, since native x/tokenization balances cannot cross IBC.

MsgJoinSwapExternAmountIn

Joins a pool with a single asset. The pool swaps part of the deposit internally so the join stays balanced. The sender specifies the exact token_in and a minimum share amount.

json
{
    "@type": "/gamm.v1beta1.MsgJoinSwapExternAmountIn",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_id": "1",
    "token_in": { "denom": "ubadge", "amount": "1000000000" },
    "share_out_min_amount": "1000000000000000"
}
proto
message MsgJoinSwapExternAmountIn {
  option (amino.name) = "gamm/JoinSwapExternAmountIn";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  uint64 pool_id = 2;
  cosmos.base.v1beta1.Coin token_in = 3;
  string share_out_min_amount = 4;                   // math.Int
}

message MsgJoinSwapExternAmountInResponse {
  string share_out_amount = 1;                       // math.Int
}
FieldTypeRequiredDescription
senderstringyesDepositor
pool_iduint64yesTarget pool
token_inCoinyesExact single-asset deposit; its denom must be a pool asset
share_out_min_amountInt stringyesSlippage floor on shares received

Behavior: the response reports the shares minted. The internal swap pays the pool's swap fee on the swapped portion.

MsgJoinSwapShareAmountOut

Single-asset join for an exact number of shares. The pool computes how much of token_in_denom it needs, capped by token_in_max_amount.

json
{
    "@type": "/gamm.v1beta1.MsgJoinSwapShareAmountOut",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_id": "1",
    "token_in_denom": "ubadge",
    "share_out_amount": "1000000000000000",
    "token_in_max_amount": "1200000000"
}
proto
message MsgJoinSwapShareAmountOut {
  option (amino.name) = "gamm/JoinSwapShareAmountOut";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  uint64 pool_id = 2;
  string token_in_denom = 3;
  string share_out_amount = 4;                       // math.Int
  string token_in_max_amount = 5;                    // math.Int
}

message MsgJoinSwapShareAmountOutResponse {
  string token_in_amount = 1;                        // math.Int
}
FieldTypeRequiredDescription
senderstringyesDepositor
pool_iduint64yesTarget pool
token_in_denomstringyesThe one asset to deposit
share_out_amountInt stringyesExact shares to receive
token_in_max_amountInt stringyesSlippage cap on the deposit

Behavior: the response reports the input actually taken.

MsgExitSwapShareAmountIn

Burns an exact number of shares and receives a single asset. The pool swaps the other assets into token_out_denom internally.

json
{
    "@type": "/gamm.v1beta1.MsgExitSwapShareAmountIn",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_id": "1",
    "token_out_denom": "ubadge",
    "share_in_amount": "1000000000000000",
    "token_out_min_amount": "900000000"
}
proto
message MsgExitSwapShareAmountIn {
  option (amino.name) = "gamm/ExitSwapShareAmountIn";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  uint64 pool_id = 2;
  string token_out_denom = 3;
  string share_in_amount = 4;                        // math.Int
  string token_out_min_amount = 5;                   // math.Int
}

message MsgExitSwapShareAmountInResponse {
  string token_out_amount = 1;                       // math.Int
}
FieldTypeRequiredDescription
senderstringyesShare holder
pool_iduint64yesPool to exit
token_out_denomstringyesThe one asset to receive
share_in_amountInt stringyesExact shares to burn
token_out_min_amountInt stringyesSlippage floor on the output

Behavior: the exit fee and the swap fee on the internally swapped portion both apply. The response reports the output amount.

MsgExitSwapExternAmountOut

Receives an exact single-asset token_out by burning at most share_in_max_amount shares.

json
{
    "@type": "/gamm.v1beta1.MsgExitSwapExternAmountOut",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_id": "1",
    "token_out": { "denom": "ubadge", "amount": "1000000000" },
    "share_in_max_amount": "1200000000000000"
}
proto
message MsgExitSwapExternAmountOut {
  option (amino.name) = "gamm/ExitSwapExternAmountOut";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  uint64 pool_id = 2;
  cosmos.base.v1beta1.Coin token_out = 3;
  string share_in_max_amount = 4;                    // math.Int
}

message MsgExitSwapExternAmountOutResponse {
  string share_in_amount = 1;                        // math.Int
}
FieldTypeRequiredDescription
senderstringyesShare holder
pool_iduint64yesPool to exit
token_outCoinyesExact single-asset output
share_in_max_amountInt stringyesSlippage cap on shares burned

Behavior: the response reports the shares actually burned.

MsgCreateStableswapPool

Creates a stableswap pool for assets that should trade near parity. Scaling factors normalize assets with different decimals.

json
{
    "@type": "/gamm.poolmodels.stableswap.MsgCreateStableswapPool",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_params": {
        "swap_fee": "0.001000000000000000",
        "exit_fee": "0.000000000000000000"
    },
    "initial_pool_liquidity": [
        { "denom": "ibc/E1116484B327AEE59CDC3DA73D319834781A13DB2A7DFC1F38A30CD45ABF58B8", "amount": "1000000000" },
        { "denom": "ibc/F082B65C88E4B6D5EF1DB243CDA1D331D002759E938A0F5CD3FFDC5D53B3E349", "amount": "1000000000" }
    ],
    "scaling_factors": ["1", "1"],
    "future_pool_governor": "",
    "scaling_factor_controller": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d"
}
proto
message MsgCreateStableswapPool {
  option (amino.name) = "gamm/CreateStableswapPool";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  PoolParams pool_params = 2;
  repeated cosmos.base.v1beta1.Coin initial_pool_liquidity = 3;
  repeated uint64 scaling_factors = 4;
  string future_pool_governor = 5;
  string scaling_factor_controller = 6;
}

message MsgCreateStableswapPoolResponse {
  uint64 pool_id = 1;
}
FieldTypeRequiredDescription
senderstringyesPool creator
pool_params.swap_feeLegacyDec stringyesSwap fee
pool_params.exit_feeLegacyDec stringyesExit fee
initial_pool_liquidityCoin[]yesInitial deposit, one entry per asset
scaling_factorsuint64[]yesOne factor per asset, in the same order as the liquidity
future_pool_governorstringnoRetained from Osmosis; governor functionality is removed on BitBadges
scaling_factor_controllerstringnoAddress allowed to send MsgStableSwapAdjustScalingFactors

Behavior: the pool ID is returned in the response. The same disablePoolCreation invariant check applies to native assets.

MsgStableSwapAdjustScalingFactors

Adjusts the scaling factors of a stableswap pool. The sender must be the pool's scaling_factor_controller.

json
{
    "@type": "/gamm.poolmodels.stableswap.MsgStableSwapAdjustScalingFactors",
    "sender": "bb1p0rrel3365scadq5k9pv0x0zp9j22js6dnw70d",
    "pool_id": "3",
    "scaling_factors": ["1", "1000"]
}
proto
message MsgStableSwapAdjustScalingFactors {
  option (amino.name) = "gamm/StableSwapAdjustScalingFactors";
  option (cosmos.msg.v1.signer) = "sender";

  string sender = 1;
  uint64 pool_id = 2;
  repeated uint64 scaling_factors = 3;
}

message MsgStableSwapAdjustScalingFactorsResponse {}
FieldTypeRequiredDescription
senderstringyesMust equal the pool's scaling_factor_controller
pool_iduint64yesStableswap pool
scaling_factorsuint64[]yesNew factors, one per asset

Behavior: the transaction fails with an unauthorized error when sender is not the controller.

Edit this page on GitHub