# MarketManager (AMM)

## `CreateMarket`

Initialises a new market, defined over a unique combination of:

* **Base token**: contract address for the base token (e.g. `ETH`) of the market pair
* **Quote token**: contract address for the quote token (e.g. `USDC`) of the market pair
* **Width**: market width which defines the precision of limit price increments (min. 1.00001 intervals)
* **Strategy**: address of the strategy contract used for managing liquidity on the market (or 0 if none)
* **Swap fee rate**: the fee rate paid by swappers to LPs, applied on amounts paid in to the pool
* **Fee controller**: address of the fee controller contract that returns the variable swap fee rate for the market (or 0 if none)
* **Controller**: address of the market controller that can define access control for various market features (e.g. enabling or disabling swaps, limit orders and strategies)

&#x20;The `market_id` is generated from the Poseidon hash of the above variables, ensuring their uniqueness. The event also emits the start limit / tick and sqrt price of the market at initialisation.

```rust
#[derive(Drop, starknet::Event)]
struct CreateMarket {
    #[key]
    market_id: felt252,
    #[key]
    base_token: ContractAddress,
    #[key]
    quote_token: ContractAddress,
    #[key]
    width: u32,
    #[key]
    strategy: ContractAddress,
    #[key]
    swap_fee_rate: u16,
    #[key]
    fee_controller: ContractAddress,
    #[key]
    controller: ContractAddress,
    start_limit: u32,
    start_sqrt_price: u256,
}
```

## `ModifyPosition`

Modifies liquidity position, either adding or removing liquidity, or collecting accrued fees. The event is also emitted for limit order updates, such that indexing all `ModifyPosition` events yields an accurate 1:1 view of available liquidity.&#x20;

* **Caller**: position owner
* **Market ID**: market id (see [above](#createmarket))
* **Lower limit**: shifted limit at which position starts
* **Upper limit**: shifted limit at which position ends
* **Is Limit Order**: true if event is emitted as part of a limit order update, false otherwise
* **Liquidity Delta**: change in liquidity applied by position update, or 0 if collecting fees only
* **Base Amount**: amount of base assets added or removed from position
* **Quote Amount**: amount of quote assets added or removed from position
* **Base Amount**: amount of base fees collected from position
* **Quote Amount**: amount of quote fees collected from position

```rust
#[derive(Drop, starknet::Event)]
struct ModifyPosition {
    #[key]
    caller: ContractAddress,
    #[key]
    market_id: felt252,
    #[key]
    lower_limit: u32,
    #[key]
    upper_limit: u32,
    #[key]
    is_limit_order: bool,
    liquidity_delta: i128,
    base_amount: i256,
    quote_amount: i256,
    base_fees: u256,
    quote_fees: u256,
}
```

## `CreateOrder`

Creates a new limit order.

* **Caller**: position owner
* **Market ID**: market id (see [above](#createmarket))
* **Order ID**: assigned unique order id
* **Limit**: shifted (lower) limit at which order is placed, i.e. the position spans `limit` to `limit` + `width`)
* **Batch ID**: ID of order batch to which order belongs (orders are batched for efficient filling)
* **Is Bid**: true if order is a bid limit order
* **Amount**: order amount

Note that this event also emits a `ModifyPosition` event (see explanation [above](#modifyposition)).

```rust
#[derive(Drop, starknet::Event)]
struct CreateOrder {
    #[key]
    caller: ContractAddress,
    #[key]
    market_id: felt252,
    #[key]
    order_id: felt252,
    #[key]
    limit: u32,
    #[key]
    batch_id: felt252,
    #[key]
    is_bid: bool,
    amount: u256,
}
```

## `CollectOrder`

Collects an existing limit order, withdrawing both filled and unfilled amounts.&#x20;

* **Caller**: position owner
* **Market ID**: market id (see [above](#createmarket))
* **Order ID**: assigned unique order id
* **Limit**: shifted (lower) limit at which order is placed, i.e. the position spans `limit` to `limit` + `width`)
* **Batch ID**: ID of order batch to which order belongs (orders are batched for efficient filling)
* **Is Bid**: true if order is a bid limit order
* **Base amount**: base amount collected
* Quote amount: quote amount collected

```rust
#[derive(Drop, starknet::Event)]
struct CollectOrder {
    #[key]
    caller: ContractAddress,
    #[key]
    market_id: felt252,
    #[key]
    order_id: felt252,
    #[key]
    limit: u32,
    #[key]
    batch_id: felt252,
    #[key]
    is_bid: bool,
    base_amount: u256,
    quote_amount: u256,
}
```

## `Swap`

Executes a swap through a single market.

* **Caller**: swap caller
* **Market ID**: market id (see [above](#createmarket))
* **Is Buy**: true if swapping from quote to base asset, false otherwise
* **Exact Input**: true if amount specified is in terms of input asset, false if in terms of output asset
* **Swap ID**: assigned unique swap id
* **Amount In**: amount swapped in (in quote tokens for buys, base tokens for sells)
* **Amount Out**: amount swapped out (in base tokens for buys, quote tokens for sells)
* **Fees**: amount swapped in (in quote tokens for buys, base tokens for sells)
* **End Limit**: shifted limit of the market after the swap
* **End Sqrt Price**: square root price of the market after the swap
* **Market Liquidity**: active market liquidity after the swap

<pre class="language-rust"><code class="lang-rust"><strong>#[derive(Drop, starknet::Event)]
</strong>struct Swap {
    #[key]
    caller: ContractAddress,
    #[key]
    market_id: felt252,
    #[key]
    is_buy: bool,
    #[key]
    exact_input: bool,
    #[key]
    swap_id: u128,
    amount_in: u256,
    amount_out: u256,
    fees: u256,
    end_limit: u32, // final limit reached after swap
    end_sqrt_price: u256, // final sqrt price reached after swap
    market_liquidity: u128, // global liquidity after swap
}
</code></pre>

## MultiSwap

A swap over multiple markets.&#x20;

* **Caller**: swap caller
* **Swap ID**: assigned unique swap id (used for identifying each leg of the multi-swap)
* **In Token**: token swapped in
* **Out Token**: token swapped out
* **Amount In**: amount swapped in
* **Amount Out**: amount swapped out

Note that individual `Swap` events are also emitted for every leg of the swap, in addition to the `MultiSwap` event.

```rust
#[derive(Drop, starknet::Event)]
struct MultiSwap {
    #[key]
    caller: ContractAddress,
    #[key]
    swap_id: u128,
    #[key]
    in_token: ContractAddress,
    #[key]
    out_token: ContractAddress,
    amount_in: u256,
    amount_out: u256,
}
```


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://haiko-docs.gitbook.io/docs/developers/events/marketmanager-amm.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
