MarketsPortfolioAnalyticsDocsCreate Market — Coming SoonTrade
𝕏
HomeDocumentation

Overview

Clutch.AMM is a permissionless NFT liquidity protocol deployed on ApeChain and Ethereum Mainnet. Markets can be deployed as either single-collection or multi-collection configurations. In multi-collection markets, collections share one token + escrow while each linked collection keeps its own AMM/loan/staking vault set. Linked collections are immutable after deployment.

The core idea: each market defines a fixed base exchange ratio (tokensPerNFT) between NFTs and its market token. The AMM quotes buys/sells around that base with fee logic. Borrowers can lock NFTs and receive market tokens immediately. Stakers earn a share of swap fees generated in the same market.

ComponentWhat it does
AMMFactoryDeploys and registers single + multi-collection markets
CollectionTokenERC-20 (+ EIP-2612 Permit) representing one market (shared across linked collections in multi mode)
TokenEscrowReserveHolds minted supply; releases tokens through bucket-gated paths
NFTAMMVaultNFT↔Token swaps: sell, random buy, specific buy
LoanVaultBorrow tokens against locked NFT collateral
NFTStakingVaultStake NFTs to earn a share of swap fees
BatchRouterExecute multi-NFT operations in a single transaction

Key Properties

  • No token release outside deterministic, audited paths.
  • Global solvency invariant checked on every release.
  • Pausable fail-safe for critical paths. Protocol admin holds PAUSER_ROLE and DEFAULT_ADMIN_ROLE for emergency controls.
  • Most market parameters are immutable after deployment. Swap fees may be adjusted via on-chain governance if the market was deployed with governance enabled.
  • Random buy selection uses on-chain FIFO inventory ordering (oldest deposited first).

AMM & Swapping

The NFTAMMVault maintains an inventory of NFTs and a corresponding token balance. Prices are derived from the floor price of NFTs already deposited. When you sell an NFT, the vault mints/releases tokens from the escrow reserve and delivers them to you (minus fees). When you buy, you pay tokens and receive an NFT from inventory.

Sell an NFT

Deposit your NFT into the vault and receive market tokens immediately. The payout equals the floor price minus swap fees. No slippage risk: set a minPayout floor to protect against last-second price movement.

sellNFT(uint256 tokenId, uint256 minPayout)
  → Reverts: SlippageExceeded if payout < minPayout
  → Reverts: NotOwner / NotApproved / WrongCollection

Buy Random NFT

Pay market tokens to receive a random NFT from the vault's inventory. Random selection uses FIFO inventory ordering on-chain (oldest deposited, first bought). The market's swap fee (randomFeeBps, configurable 1–15%) applies.

buyRandomNFT(uint256 maxCost)
  → Reverts: EmptyInventory / SlippageExceeded if cost > maxCost

Buy Specific NFT

Pay a higher fee (specificFeeBps, which must be ≥ randomFeeBps) to select a specific NFT from the vault by token ID. This prevents gaming the rarity floor while still allowing targeted buys for collectors.

buySpecificNFT(uint256 tokenId, uint256 maxCost)
  → Reverts: NotInInventory / SlippageExceeded

Fee Structure

OperationStaker FeeProtocol FeeTotal
Sell NFTrandomFeeBps (1–15%)0.5%randomFeeBps + 0.5%
Buy Random NFTrandomFeeBps (1–15%)0.5%randomFeeBps + 0.5%
Buy SpecificspecificFeeBps (≥ randomFeeBps)0.5%specificFeeBps + 0.5%
The protocol fee is fixed at 0.5% on all operations. Staker fees (randomFeeBps, specificFeeBps) are set per market at deployment and distributed to stakers proportionally to their NFT stake weight. Protocol fees go to the Clutch DAO treasury.

Borrowing

Lock your NFT as collateral and receive market tokens instantly. The loan is fixed-term: you choose a duration between 1 and 365 days. Interest accrues at the market's fixed APY. Repay the principal plus accrued interest before the grace period ends to retrieve your NFT.

How it works

  • Open a loan: your NFT is escrowed in the LoanVault for the loan duration.
  • Receive tokens: principal is released from the Loan bucket of the escrow reserve.
  • Repay: return principal + interest before maturity + 7-day grace period.
  • NFT returned: once repayment is confirmed, your NFT is released back to your wallet.
  • Liquidation: if unpaid after the grace period, any address can liquidate and earn a 2% incentive.

Loan Parameters

ParameterValue
Borrow APYSet per market at deployment (immutable)
Min Duration1 day
Max Duration365 days
Grace Period7 days after maturity
LiquidationPermissionless after grace period
Max LTV100% (1 NFT = principal equal to floor)
Failure to repay within the 7-day grace period results in permanent loss of your NFT. Set calendar reminders before your maturity date.

Contract Signatures

borrow(uint256 tokenId, uint256 duration)
  → Reverts: DurationTooShort / DurationTooLong / MaxLoansExceeded

repay(uint256 loanId)
  → Repays principal + interest; returns NFT
  → Reverts: LoanNotActive / NotBorrower

liquidate(uint256 loanId)
  → Permissionless after grace period; caller receives 2% incentive
  → Reverts: GraceNotExpired / LoanNotActive

getLoanDetails(uint256 loanId)
  → Returns borrower, tokenId, principal, maturity, graceDeadline, status

Staking & Rewards

Deposit your NFTs into the NFTStakingVault to earn a continuous share of all swap fees generated by the market. Rewards accumulate in real-time and can be claimed at any time as market tokens.

Reward Sources

SourceStaker ShareNotes
Random buy feesRandom-fee bucketDistributed every block
Specific buy feesSpecific-fee bucketHigher fee rate (≥ random fee)
Sell feesRandom-fee bucketDistributed every block

Staking Lifecycle

  • Stake: transfer NFT into the staking vault. Start accumulating rewards immediately.
  • Claim: call claimRewards() at any time to receive accumulated market tokens.
  • Unstake: call unstake(tokenId) after the 24-hour cooldown has elapsed.
  • Return: unstake transfers your NFT back to your wallet in the same transaction.
stake(uint256 tokenId)
unstake(uint256 tokenId)      // requires cooldown to be elapsed
claimRewards()                // claim accumulated market tokens
pendingRewards(address user)
Your reward share is proportional to your staked NFT count vs. the total staked supply. More staked NFTs → higher share of the fee stream.

Create a Market

Any ERC-721 collection on a supported chain can have a Clutch.AMM market deployed for it. ERC-1155 support is available at the contract level; UI support is coming soon. Markets are permissionless — no approval needed. Multiple independent markets can exist for the same collection (each with its own parameters). The factory assigns each market a unique incrementing ID and deploys a fresh set of contracts for every market.

Deployment Process

  • Provide the primary collection address, then optionally add more collections for a multi-collection market.
  • Define the collection token name, symbol, and how many tokens each NFT is worth.
  • Set fee parameters: random buy fee, specific buy fee, and borrow APY. Protocol fee is fixed at 0.5%.
  • Pay the deployment fee (if any) to the factory. The fee is set by the protocol admin and may be zero.
  • The factory deploys all required contracts (token, escrow, AMM vault, loan vault, staking vault — plus an optional governance contract), mints the total supply into escrow, and registers the market with a unique ID.

Deployment Parameters & Bounds

ParameterMinMaxNotes
tokensPerNFT1001,000,000Sets the AMM exchange rate; defines 1 NFT = N tokens
randomBuyFee1%15%Applied to random buys and sells (staker portion)
specificBuyFee≥ randomBuyFee15%Must be ≥ randomBuyFee
protocolFee0.5%0.5%Fixed at 0.5% — goes to Clutch DAO treasury
borrowAPY1%50%Fixed for the lifetime of the market
deployFee0Set by admin; currently free
Immutable core market config. tokensPerNFT, totalSupply, bucket caps, and borrowAPY cannot be changed after deployment. There is no upgrade path for these parameters. The protocol admin retains DEFAULT_ADMIN_ROLE and PAUSER_ROLE for pause/unpause and emergency controls. Review every value carefully before confirming.

Solvency & Safety

The protocol enforces a global solvency invariant on every token release. The invariant guarantees that the total tokens in circulation can never exceed the tokens held in escrow minus the permanently locked portion. It is checked on every call to the TokenEscrowReserve and monitored off-chain by the risk engine.

The Invariant

// Must hold at all times (checked in TokenEscrowReserve.release() and returnTokens()):
escrow.balanceOf(escrow) + totalReleased >= totalSupply

// In plain terms: tokens held in escrow + tokens already out ≥ total minted.
// Protects against any out-of-thin-air token release.
// If this check fails, the transaction reverts with InvariantViolation.

Bucket Architecture

Token releases are gated by three isolated buckets. Each bucket has a hard cap. Once a bucket reaches its cap, no further releases from that path are possible, protecting the other paths.

BucketFunded byCap
AMM ReserveSwap buysSet at deployment (ammBps % of totalSupply)
Loan ReserveBorrowersSet at deployment (loanBps % of totalSupply)
Reward ReserveFee incomeLaunch cap is fixed to 0; rewards are fee-funded only
Launch allocation is policy-constrained: rewardBps must be 0 and loanBps is capped at 5% . Any unallocated portion remains in escrow unless released through protocol-defined paths.

Fail-Safes

  • Emergency pause: any vault can be paused by the protocol admin (PAUSER_ROLE). Unpausing requires DEFAULT_ADMIN_ROLE.
  • Bucket caps: each release path (AMM, Loan, Reward) has a hard cap set at deployment; once reached, no further releases from that path.
  • Invariant breach: if the global invariant fails after any release, the transaction reverts automatically with InvariantViolation.
  • Liquidation bot: open-source reference liquidator monitors all loans for expiry.
  • No admin drain: escrow only releases tokens via authorized vault contracts. The admin cannot withdraw tokens directly.

Smart Contracts

The table below shows the contracts currently configured in this frontend environment. For local Anvil sessions, these are local development addresses. The factory is the single entry point for deploying new markets.

Deployed Addresses

ContractAddressNetwork
AMMFactory0x87B62309B6fF4FA184C89919351bEbd3AC11Fc84ApeChain (33139)
BatchRouter0x1577A7E3740846885610B9Be89886008D977AfDcApeChain (33139)
CamelotListingRequestNot configuredApeChain (33139)
AMMFactory0xEA095646EC6A56EDbFEe84cCcf23eFCec12566A0Ethereum (1)

Key Function Reference

// Factory
struct CreateMarketParams {
  address collection;
  string name;
  string symbol;
  uint256 tokensPerNFT;
  uint256 totalSupply;
  FeeConfig fees;            // { randomFeeBps, specificFeeBps }
  BucketConfig buckets;      // { ammBps, loanBps, rewardBps } — must sum <= 100%
  uint16 borrowAPYBps;
  uint16 liquidationIncentiveBps;
  GovernanceParams governance; // { enabled, proposalFee, minProposerStake }
}

struct CreateMultiCollectionParams {
  string name;
  string symbol;
  uint256 totalSupply;
  BucketConfig buckets;
  uint16 liquidationIncentiveBps;
  GovernanceParams governance;
  CollectionConfig[] collections; // per-collection: { collection, tokensPerNFT, fees, borrowAPYBps }
}

createMarket(CreateMarketParams p) payable → MarketInfo
createMultiCollectionMarket(CreateMultiCollectionParams p) payable → MarketInfo

allMarkets() view → MarketInfo[]
marketCount() view → uint256
getCollectionsForMarket(uint256 marketId) view → address[]
getCollectionVaultInfo(uint256 marketId, address collection) view → CollectionVaultInfo

// NFTAMMVault
sellNFT(uint256 tokenId, uint256 minPayout)
buyRandomNFT(uint256 maxCost)
buySpecificNFT(uint256 tokenId, uint256 maxCost)
quoteRandomBuy() view → (totalCost, baseCost, fee, protocolFee, inventorySize, nextTokenId)
quoteSpecificBuy(uint256 tokenId) view → (totalCost, baseCost, fee, protocolFee, available)

// LoanVault
borrow(uint256 tokenId, uint256 duration)
repay(uint256 loanId)
liquidate(uint256 loanId)
getLoanDetails(uint256 loanId) view → LoanInfo

// NFTStakingVault
stake(uint256 tokenId)
unstake(uint256 tokenId)
claimRewards()
pendingRewards(address user) view → uint256
All function signatures follow Solidity ABI encoding. Use viem or ethers.js to interact with contracts directly, or use the Clutch.AMM frontend for a guided experience.

UI Metrics Note

Market cap is displayed as a token-denominated value using the market's native token symbol (e.g. 21.89M TEST). For multi-collection markets, the label reads Est. Market Cap because capacity is derived from shared escrow sizing rather than per-collection hard allocation. TVL is shown as the number of NFTs currently held in protocol vaults.

When you deploy a new market, the protocol creates a brand-new ERC-20 token for your collection. By default, wallets and block explorers will show a placeholder icon. Follow these steps to get your token logo displayed across the ecosystem.

How Clutch.AMM resolves token logos

The app tries the following sources in order, using the first one that loads successfully:

PrioritySourceHow to set it
1. FastestCustom URL (your DB record)Paste a URL when creating your market. Stored in the Clutch.AMM backend and shown immediately
2Trust Wallet Assets GitHubOpen a PR to trustwallet/assets repo with your logo file
3Clutch token-assets repoSubmit via Discord. Logo added to clutchmarkets/token-assets
4. Always worksInitials fallbackAuto-generated from your token symbol. No action needed

Option 1: Self-host (instant)

This is the fastest path. Host a square PNG or SVG anywhere (IPFS, Arweave, GitHub, CDN), then paste the URL into the Token Logo field when creating your market. The URL is stored in our backend and shown everywhere on Clutch.AMM immediately.

Recommended format: 256×256px square PNG with transparent background. Avoid JPEGs. They don't handle transparency.
# Good logo URLs:
https://ipfs.io/ipfs/QmXxx.../logo.png
https://arweave.net/TXID/logo.png
https://raw.githubusercontent.com/yourorg/assets/main/cpup.png
https://cdn.yourproject.com/token-logo.png

Option 2: Block Explorer (recommended)

Your chain's block explorer (ApeScan for ApeChain, Etherscan for Ethereum) allows token issuers to upload a logo that appears on the token page and in MetaMask's token import flow.

  • 1.Deploy your market (this creates the ERC-20 token on-chain).
  • 2.Go to your chain's block explorer and search for your token contract address.
  • 3.Click 'Update Token Info' on the token page.
  • 4.Fill in the token info form and upload your logo PNG (max 1MB, square).
  • 5.Submit. Verification usually takes 24-48 hours.

Option 3: Trust Wallet Assets

Trust Wallet maintains an open-source repository of token logos used by Trust Wallet, MetaMask, and many other wallets. Getting listed here gives the broadest ecosystem coverage.

# Repository structure:
trustwallet/assets/
  blockchains/
    apechain/
      assets/
        0xYourTokenAddress/   ← checksummed ERC-55 address
          logo.png            ← 256×256px, max 100KB

# Steps:
1. Fork https://github.com/trustwallet/assets
2. Create the directory at the path above
3. Add your logo.png (256×256, transparent bg)
4. Open a Pull Request — usually merged in 1–3 days
Trust Wallet requires the directory name to be the EIP-55 checksummed address (mixed case). Use a checksum tool or call ethers.getAddress(address) to get the correct casing.

After listing

Once your logo is live anywhere (self-hosted URL, ApeScan, or Trust Wallet), update your market's token logo URL in the market metadata editor (owner-only on the market page) or set it during market creation. The change propagates site-wide immediately.

Risk Disclosure

Clutch.AMM is experimental software. Interact only with funds you can afford to lose.

Smart Contract Risk

Despite thorough testing and audit processes, all smart contracts carry the risk of undiscovered vulnerabilities. A bug could result in partial or total loss of funds.

Liquidation Risk

If you take out a loan and do not repay before the grace period ends, your NFT collateral will be permanently liquidated. There is no recovery mechanism. The liquidation is irreversible on-chain.

Market Risk

NFT floor prices can move rapidly. A sharp decline in floor price reduces the collateral value of your NFT. While Clutch.AMM uses fixed-rate loans (not mark-to-market LTV), the token payout you receive when selling is directly tied to current floor conditions.

Liquidity Risk

If the vault's NFT inventory is empty, random and specific buys will fail until new NFTs are deposited. If the escrow bucket reaches its cap, swaps in that direction may temporarily be unavailable.

Oracle & Randomness Risk

Random buy selection uses FIFO inventory ordering (oldest deposited, first purchased). This avoids external oracle dependencies, but users should still assume NFT purchase outcomes depend on current vault inventory state at execution time.

Audit

Clutch.AMM contracts have undergone a comprehensive security audit covering all 14 Solidity source files (2,779 SLOC) across the factory, market, vault, governance, router, and library modules. The audit has been certified by Hashlock.

Hashlock Certified — PASSED
Zero vulnerabilities identified across all severity levels. Full clean report.
AuditorScopeStatusResult
HashlockFull contract suite (14 contracts, 2,779 SLOC)CompletePASSED
Community / ImmuneFiBug bounty programActive at launchOngoing
The full audit report includes executive summary, architecture review, reentrancy analysis, arithmetic safety verification, escrow invariant proofs, governance security analysis, and complete test coverage details.
Do not interact with unverified contract addresses. Always confirm you are on the official Clutch.AMM frontend at clutch.market before signing any transaction.