> For the complete documentation index, see [llms.txt](https://docs.tonco.io/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.tonco.io/contracts-v1.6-forthcoming/scenarios.md).

# Scenarios

* Scenarios
  * [Deploy/Init Pool](#deploy-init-pool)
  * [Mint](#mint)
  * [Swap](#swap)
  * [Burn](#burn-and-collect)

## Scenarios

### Deploy/Init Pool (WIP)

Pool deployment is triggered by the administrator of the AMM (this person is also the administrator of the router contract - `router::admin_address`) or by specific roles - pool factory (`router::pool_factory_address`) and pool admin (`router::pool_admin_address`). It is done by invoking the operation [CREATE\_POOL](/contracts-v1.6-forthcoming/router.md#router_create_pool). Pool deployment leads to the processing of the [POOL\_INIT](/contracts-v1.6-forthcoming/pool.md#pool_init) operation inside the pool contract. This operation is used both - during the initial pool deployment and when the pool administrator wants to change some crucial parameters. Pool deployment consists of two stages

I. Forming and sending state\_init data

The state\_init code is not the actual pool code, but a basic immutable pool prototype (router::subcodes.pool\_prototype\_code). The state\_init data holds only the fields that define the pool identity:

* Router address
* Jetton0/Jetton1 wallet addresses (these are attached to the router; they are ordered by address hash, so for any pair of jettons there is exactly one possible pool address)

All other storage fields are set to defaults: the pool is marked as not deployed, and the admin and controller addresses are set to BLACK\_HOLE\_ADDRESS.

Since the pool address is fully determined by the router address and the two jetton wallets, anyone can compute it off-chain, and the same prototype code can be reused for every pool while the actual pool code stays upgradable at deploy time.

II. The state\_init message holds as a body the POOL\_INIT operation

This message carries everything the prototype needs to become a working pool:

* The actual Pool contract code — the prototype replaces its own code with it via set\_code
* Account contract code
* Position NFT contract code
* Pool parameters: tick spacing, initial price, fees, activity flag
* Pool roles: admin, controller, creator (and, when sent by the router admin, also arbiter, ALM and oracle)

Newly created pool starts in a "not deployed" state: the is\_deployed flag in state\_init is set to false, and the admin address is set to BLACK\_HOLE\_ADDRESS. While the pool is not deployed, every operation except POOL\_INIT is rejected. POOL\_INIT itself is only accepted from the router or from the pool admin. Since the admin in state\_init is BLACK\_HOLE\_ADDRESS (an address nobody controls), the only party that can perform the initial deployment is the router. And because the pool address is derived from the state\_init that contains the router address, nobody can deploy a pool at the "canonical" address with a different router or a pre-set admin — any tampering with the initial data changes the resulting address. After the initial deployment, POOL\_INIT can be repeated to change crucial parameters, but only when it originates from the router admin or the pool admin: an init message proxied by the router on behalf of the pool factory carries a flag that forbids re-initialization of an already deployed pool.

<figure><img src="/files/RA64QaJ9LEwnGLAtpjG0" alt=""><figcaption></figcaption></figure>

#### Pool Factory

Pool factory is expected to be a contract callable for anyone. It checks on-chain data validity for pool creation. The pool created by pool factory can only have a predefined number of fee and tick spacing settings

**Pool Settings**

When creating a pool through the Pool Factory, the `settings` field selects one of the predefined fee / tick spacing combinations:

| settings        | LP fee | Tick spacing | Fee, % |
| --------------- | ------ | ------------ | ------ |
| 1               | 5      | 10           | 0.05%  |
| 2               | 30     | 60           | 0.3%   |
| 3               | 100    | 200          | 1%     |
| any other value | 1      | 1            | 0.01%  |

LP fee is expressed in units of 1/10000 (0.01%). The protocol fee is fixed by the factory and cannot be chosen. Pools created through the factory are activated immediately. Custom fee and tick spacing values are only available to addresses whitelisted by the factory administrator.

**Jetton Requirements**

Permissionless pool creation works with any jetton whose minter supports **on-chain wallet discovery (**[**TEP-89**](https://github.com/ton-blockchain/TEPs/blob/master/text/0089-jetton-wallet-discovery.md)**)**:

* The minter must handle `provide_wallet_address` (op `0x2c76b973`) and reply with `take_wallet_address` (op `0xd1735400`).

The factory does not trust jetton wallet addresses supplied by the caller. Instead, it deploys a temporary order contract (one per jetton pair) that queries both jetton minters on-chain for the router's wallet addresses. Only after **both** minters respond does the factory proceed with pool creation. If a minter does not implement TEP-89, the discovery never completes and the pool cannot be created through the permissionless flow.

No other on-chain methods are required from the jetton.

If your jetton doesn't support TEP-89 please contact the team and we will gladly help you with pool creation

### Mint

Position minting is done by sending two jettons to the router. Generally, the user calls pool::getMintEstimate to estimate the number of jettons that the person needs to send to mint a particular amount of liquidity in the given price range (tick range). Optionally, the user may send more jettons than needed to account for possible slippage.

While sending both jettons to router wallets, the user sends the payload that contains the position parameters. On receiving the jettons (operation [JETTON\_TRANSFER\_NOTIFICATION](/contracts-v1.6-forthcoming/router.md#routerv3_transfer_notification) ) router would compute the pool address and forward the operation to the pool ([POOL\_FUND\_ACCOUNT](/contracts-v1.6-forthcoming/pool.md#pool_fund_account))

The pool uses a special structure - user Account ([Account](/contracts-v1.6-forthcoming/account.md)) to create a barrier that would collect the proof that two jettons are funded and order to mint liquidity and then send it back to the pool for actual mint execution

<figure><img src="/files/g06SlK0lB5lJI83VrSmM" alt=""><figcaption></figcaption></figure>

### Swap

Generally user calls [pool::getSwapEstimate](/contracts-v1.6-forthcoming/pool.md#getswapestimate) to estimate the amount of the jettons that he/she needs to send to swap and then sends jettons to the router with a payload describing the future swap. The router forwards the swap to the pool by dynamically computing the pool address.

<figure><img src="/files/Tog6PfScEtzh1eUDdBL2" alt="" width="800"><figcaption></figcaption></figure>

### Burn and Collect

There are two ways that can trigger the burn.

<figure><img src="/files/HhSPvyh48hot7hTxgaGQ" alt="" width="400"><figcaption><p>Burn via Pool</p></figcaption></figure>

<figure><img src="/files/JZd4ZklprhdWLyhiRTUM" alt="" width="400"><figcaption><p>Burn via Text</p></figcaption></figure>

### Getter

Here is an example of the onchain getter, that is obviously async, but can be useful sometimes

<figure><img src="/files/s5mZ5G9Ifa5qgBujI8RY" alt="" width="400"><figcaption><p>Getter</p></figcaption></figure>


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## 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://docs.tonco.io/contracts-v1.6-forthcoming/scenarios.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.
