From 9329244ba89c141133d18b32c34ec38592086c69 Mon Sep 17 00:00:00 2001 From: Badi Ifaoui Date: Sat, 11 Apr 2026 16:18:48 +0100 Subject: [PATCH 1/2] chore: remove unnecessary environment variables and service dependency from docker-compose.yml for grow-dex-indexer --- examples/grow-dex-indexer/docker-compose.yml | 8 -------- 1 file changed, 8 deletions(-) diff --git a/examples/grow-dex-indexer/docker-compose.yml b/examples/grow-dex-indexer/docker-compose.yml index e48b78c..f10e9a1 100644 --- a/examples/grow-dex-indexer/docker-compose.yml +++ b/examples/grow-dex-indexer/docker-compose.yml @@ -20,14 +20,6 @@ services: ports: - '4000:4000' - '4001:4001' - environment: - AE_MDW_DB_HOST: postgres - AE_MDW_DB_NAME: ae_mdw - AE_MDW_DB_USER: postgres - AE_MDW_DB_PASSWORD: postgres - depends_on: - postgres: - condition: service_healthy grow-dex-indexer: build: From 1702188bbd82eec0ca1d56c50fa6021ba04bfbc5 Mon Sep 17 00:00:00 2001 From: Badi Ifaoui Date: Wed, 15 Apr 2026 07:39:13 +0100 Subject: [PATCH 2/2] feat: bcl indexer example --- examples/bcl-indexer/.env.example | 9 + examples/bcl-indexer/.gitignore | 5 + examples/bcl-indexer/README.md | 178 ++ .../AffiliationBondingCurveTokenSale.aci.json | 1562 ++++++++++ .../abis/AffiliationTreasury.aci.json | 393 +++ .../bcl-indexer/abis/BondingCurve.aci.json | 148 + .../abis/BondingCurveExponential.aci.json | 287 ++ .../abis/CommunityFactory.aci.json | 2595 +++++++++++++++++ .../abis/CommunityManagement.aci.json | 301 ++ examples/bcl-indexer/abis/DAO.aci.json | 1365 +++++++++ examples/bcl-indexer/abis/DAOVote.aci.json | 707 +++++ examples/bcl-indexer/abis/TokenSale.aci.json | 503 ++++ .../bcl-indexer/abis/bytecode_hashes.json | 32 + examples/bcl-indexer/abis/source_hashes.json | 11 + examples/bcl-indexer/aesync-env.d.ts | 37 + examples/bcl-indexer/aesync.config.ts | 36 + examples/bcl-indexer/docker-compose.yml | 19 + examples/bcl-indexer/package.json | 15 + examples/bcl-indexer/schema.ts | 78 + examples/bcl-indexer/src/api/index.ts | 68 + examples/bcl-indexer/src/factory.ts | 29 + examples/bcl-indexer/src/index.ts | 8 + examples/bcl-indexer/src/token-sale.ts | 106 + examples/bcl-indexer/tsconfig.json | 14 + examples/grow-dex-indexer/aesync.config.ts | 2 +- packages/core/src/aci/aci.test.ts | 4 +- packages/core/src/aci/decoder.ts | 41 + packages/core/src/aci/hash.ts | 20 +- packages/core/src/aci/parser.ts | 27 +- packages/core/src/bin/aesync.ts | 2 +- packages/core/src/build/build.test.ts | 13 +- packages/core/src/build/contracts.ts | 11 +- packages/core/src/build/index.ts | 12 +- packages/core/src/build/indexing.ts | 4 +- packages/core/src/build/plugin.ts | 17 +- packages/core/src/database/migrate.ts | 24 + packages/core/src/mdw/http.ts | 2 +- packages/core/src/sync/historical.ts | 20 +- packages/core/src/sync/index.ts | 7 +- packages/core/src/sync/sync.test.ts | 2 +- packages/core/src/sync/types.ts | 2 + pnpm-lock.yaml | 6 + 42 files changed, 8681 insertions(+), 41 deletions(-) create mode 100644 examples/bcl-indexer/.env.example create mode 100644 examples/bcl-indexer/.gitignore create mode 100644 examples/bcl-indexer/README.md create mode 100644 examples/bcl-indexer/abis/AffiliationBondingCurveTokenSale.aci.json create mode 100644 examples/bcl-indexer/abis/AffiliationTreasury.aci.json create mode 100644 examples/bcl-indexer/abis/BondingCurve.aci.json create mode 100644 examples/bcl-indexer/abis/BondingCurveExponential.aci.json create mode 100644 examples/bcl-indexer/abis/CommunityFactory.aci.json create mode 100644 examples/bcl-indexer/abis/CommunityManagement.aci.json create mode 100644 examples/bcl-indexer/abis/DAO.aci.json create mode 100644 examples/bcl-indexer/abis/DAOVote.aci.json create mode 100644 examples/bcl-indexer/abis/TokenSale.aci.json create mode 100644 examples/bcl-indexer/abis/bytecode_hashes.json create mode 100644 examples/bcl-indexer/abis/source_hashes.json create mode 100644 examples/bcl-indexer/aesync-env.d.ts create mode 100644 examples/bcl-indexer/aesync.config.ts create mode 100644 examples/bcl-indexer/docker-compose.yml create mode 100644 examples/bcl-indexer/package.json create mode 100644 examples/bcl-indexer/schema.ts create mode 100644 examples/bcl-indexer/src/api/index.ts create mode 100644 examples/bcl-indexer/src/factory.ts create mode 100644 examples/bcl-indexer/src/index.ts create mode 100644 examples/bcl-indexer/src/token-sale.ts create mode 100644 examples/bcl-indexer/tsconfig.json diff --git a/examples/bcl-indexer/.env.example b/examples/bcl-indexer/.env.example new file mode 100644 index 0000000..4a26b94 --- /dev/null +++ b/examples/bcl-indexer/.env.example @@ -0,0 +1,9 @@ +# ae-mdw connection (live mainnet) +AE_MDW_URL=https://mainnet.aeternity.io/mdw +AE_MDW_WS_URL=wss://mainnet.aeternity.io/mdw/v3/websocket + +# Database +DATABASE_URL=postgresql://postgres:postgres@localhost:5432/bcl + +# Network +AE_NETWORK=mainnet diff --git a/examples/bcl-indexer/.gitignore b/examples/bcl-indexer/.gitignore new file mode 100644 index 0000000..6ba8bc9 --- /dev/null +++ b/examples/bcl-indexer/.gitignore @@ -0,0 +1,5 @@ +node_modules/ +dist/ +.aesync/ +.env +*.log diff --git a/examples/bcl-indexer/README.md b/examples/bcl-indexer/README.md new file mode 100644 index 0000000..70128c3 --- /dev/null +++ b/examples/bcl-indexer/README.md @@ -0,0 +1,178 @@ +# BCL Indexer + +A production-ready [aesync](../../README.md) indexer for the **Bonding Curve Launchpad (BCL)** on Aeternity. Tracks token creation, buy/sell transactions, and price changes, then exposes the data through REST and GraphQL APIs. + +## What it indexes + +| Contract | Events | Purpose | +|---|---|---| +| **CommunityFactory** | `CreateCommunity` | Discovers new BCL tokens on-chain | +| **AffiliationBondingCurveTokenSale** | `Buy`, `Sell`, `PriceChange` | Records trades and price movements | + +### Schema + +- **`token`** — BCL token metadata (address, name, DAO, community management) +- **`transaction`** — every buy/sell with amounts, fees, and involved token +- **`price_change`** — price movement history per token +- **`token_day_data`** — daily aggregated volume and price snapshots + +## Setup + +### Prerequisites + +- Node.js >= 18 +- PostgreSQL 14+ + +### Local development + +```bash +# Install dependencies (from the aesync monorepo root) +pnpm install + +# Start Postgres +docker compose up -d + +# Copy env and configure +cp .env.example .env +# Edit .env if needed — defaults point to live mainnet MDW + +# Run in dev mode (auto-reload) +pnpm dev +``` + +### Docker (Postgres only) + +```bash +docker compose up -d +``` + +This starts PostgreSQL for the indexer. The indexer itself connects to the live ae-mdw at `mainnet.aeternity.io`. + +### Configuration + +Edit `aesync.config.ts` to change: +- Network (mainnet/testnet) +- `startHeight` to begin indexing from a specific block +- Database connection + +## API + +### REST endpoints + +| Method | Path | Description | +|---|---|---| +| `GET` | `/tokens` | List all indexed tokens | +| `GET` | `/tokens/:address` | Single token details | +| `GET` | `/tokens/:address/transactions?limit=50` | Recent buys/sells for a token | +| `GET` | `/tokens/:address/price-history?limit=50` | Price change history for a token | +| `GET` | `/stats` | Global stats (total tokens, buys, sells, price changes) | +| `GET` | `/health` | Sync status and health check | + +### GraphQL + +Available at `http://localhost:42069/graphql`. Example queries: + +```graphql +# All tokens +{ + tokens(first: 10) { + items { + address + name + daoAddress + communityManagementAddress + createdAtHeight + } + pageInfo { hasNextPage endCursor } + } +} + +# Recent transactions for a token +{ + transactions( + first: 20 + where: { tokenSaleAddress: "ct_..." } + orderBy: "height" + orderDirection: DESC + ) { + items { + type + tokenAmount + aeAmount + fee + txHash + height + } + } +} + +# Price history +{ + priceChanges( + first: 30 + where: { tokenSaleAddress: "ct_..." } + orderBy: "height" + orderDirection: DESC + ) { + items { + oldPrice + newPrice + txHash + height + } + } +} + +# Daily aggregated data +{ + tokenDayDatas( + first: 30 + where: { tokenSaleAddress: "ct_..." } + orderBy: "date" + orderDirection: DESC + ) { + items { + date + dailyBuyCount + dailySellCount + dailyBuyVolume + dailySellVolume + price + } + } +} +``` + +## Architecture + +``` +┌─────────────────────────────────────────────┐ +│ Aeternity │ +│ (mainnet) │ +└─────────┬───────────────────────────────────┘ + │ blocks + contract logs +┌─────────▼───────────────────────────────────┐ +│ mainnet.aeternity.io/mdw │ +│ (live middleware) │ +└─────────┬───────────────────────────────────┘ + │ HTTP + WebSocket +┌─────────▼───────────────────────────────────┐ +│ aesync engine │ +│ ┌────────────┐ ┌───────────────────────┐ │ +│ │ Factory │ │ TokenSale │ │ +│ │ handler │ │ handlers (per-token) │ │ +│ └────┬───────┘ └────┬──────────────────┘ │ +│ └──────────┬────┘ │ +│ ┌─────▼──────┐ │ +│ │ PostgreSQL │ │ +│ └─────┬──────┘ │ +│ ┌─────▼──────┐ │ +│ │ REST API │ │ +│ │ GraphQL │ │ +│ └────────────┘ │ +└─────────────────────────────────────────────┘ +``` + +## License + +MIT diff --git a/examples/bcl-indexer/abis/AffiliationBondingCurveTokenSale.aci.json b/examples/bcl-indexer/abis/AffiliationBondingCurveTokenSale.aci.json new file mode 100644 index 0000000..607a070 --- /dev/null +++ b/examples/bcl-indexer/abis/AffiliationBondingCurveTokenSale.aci.json @@ -0,0 +1,1562 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "String", + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Transfer": ["address", "address", "int"] + }, + { + "Allowance": ["address", "address", "int"] + }, + { + "Burn": ["address", "int"] + }, + { + "Mint": ["address", "int"] + }, + { + "Swap": ["address", "int"] + } + ] + }, + "functions": [ + { + "arguments": [], + "name": "aex9_extensions", + "payable": false, + "returns": { + "list": ["string"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "name", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "initial_owner_balance", + "type": { + "option": ["int"] + } + } + ], + "name": "init", + "payable": false, + "returns": "FungibleTokenFull.state", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "FungibleTokenFull.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "total_supply", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "balances", + "payable": false, + "returns": "FungibleTokenFull.balances", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "balance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "swapped", + "payable": false, + "returns": { + "map": ["address", "int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "allowances", + "payable": false, + "returns": "FungibleTokenFull.allowances", + "stateful": false + }, + { + "arguments": [ + { + "name": "allowance_accounts", + "type": "FungibleTokenFull.allowance_accounts" + } + ], + "name": "allowance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + } + ], + "name": "allowance_for_caller", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "create_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value_change", + "type": "int" + } + ], + "name": "change_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + } + ], + "name": "reset_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "value", + "type": "int" + } + ], + "name": "burn", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "mint", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "swap", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "check_swap", + "payable": false, + "returns": "int", + "stateful": true + } + ], + "kind": "contract_child", + "name": "FungibleTokenFull", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "total_supply", + "type": "int" + }, + { + "name": "balances", + "type": "FungibleTokenFull.balances" + }, + { + "name": "meta_info", + "type": "FungibleTokenFull.meta_info" + }, + { + "name": "allowances", + "type": "FungibleTokenFull.allowances" + }, + { + "name": "swapped", + "type": { + "map": ["address", "int"] + } + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "record": [ + { + "name": "name", + "type": "string" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + } + ] + }, + "vars": [] + }, + { + "name": "allowance_accounts", + "typedef": { + "record": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "for_account", + "type": "address" + } + ] + }, + "vars": [] + }, + { + "name": "balances", + "typedef": { + "map": ["address", "int"] + }, + "vars": [] + }, + { + "name": "allowances", + "typedef": { + "map": ["FungibleTokenFull.allowance_accounts", "int"] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "token_contract", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "sale_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "address" + } + ], + "name": "buy_with_affiliation", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + } + ], + "name": "set_beneficiary", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [], + "name": "beneficiary", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "TokenSale", + "payable": false, + "typedefs": [] + } + }, + { + "namespace": { + "name": "Frac", + "typedefs": [ + { + "name": "frac", + "typedef": { + "variant": [ + { + "Pos": ["int", "int"] + }, + { + "Zero": [] + }, + { + "Neg": ["int", "int"] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "supported_decimals", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "curve_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "sell_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "calculate_buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "calculate_sell_return", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "sell_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "BondingCurve", + "payable": false, + "typedefs": [] + } + }, + { + "namespace": { + "name": "Option", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Pair", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Set", + "typedefs": [ + { + "name": "set", + "typedef": { + "record": [ + { + "name": "to_map", + "type": { + "map": ["'a", "unit"] + } + } + ] + }, + "vars": [ + { + "name": "'a" + } + ] + } + ] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "ChangeMinimumTokenThreshold": ["int"] + }, + { + "AddModerator": ["address"] + }, + { + "DeleteModerator": ["address"] + }, + { + "MuteUserId": ["string"] + }, + { + "UnmuteUserId": ["string"] + }, + { + "SetOwner": ["address"] + }, + { + "ChangedMetaInfo": [] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "initial_moderator", + "type": "address" + }, + { + "name": "minimum_token_threshold", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "init", + "payable": false, + "returns": "CommunityManagement.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "CommunityManagement.state", + "stateful": false + }, + { + "arguments": [], + "name": "moderator_accounts", + "payable": false, + "returns": { + "Set.set": ["address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "muted_user_ids", + "payable": false, + "returns": { + "Set.set": ["string"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "minimum_token_threshold", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "CommunityManagement.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "minimum_token_threshold", + "type": "int" + } + ], + "name": "change_minimum_token_threshold", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "moderator", + "type": "address" + } + ], + "name": "add_moderator", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "moderator", + "type": "address" + } + ], + "name": "delete_moderator", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "user_id", + "type": "string" + } + ], + "name": "mute_user_id", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "user_id", + "type": "string" + } + ], + "name": "unmute_user_id", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "change_meta_info", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "owner", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_child", + "name": "CommunityManagement", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "minimum_token_threshold", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "moderator_accounts", + "type": { + "Set.set": ["address"] + } + }, + { + "name": "muted_user_ids", + "type": { + "Set.set": ["string"] + } + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "map": ["string", "string"] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "is_dao", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "get_community_management", + "payable": false, + "returns": { + "option": ["CommunityManagement"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "record_sale_transaction", + "payable": true, + "returns": "unit", + "stateful": true + } + ], + "kind": "contract_interface", + "name": "ReplaceableDAO", + "payable": false, + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "UserInvited": ["address", "address"] + }, + { + "RewardAdded": ["address", "int"] + }, + { + "Withdrawn": ["address", "int"] + }, + { + "InvitationRegistered": ["address", "address", "int"] + }, + { + "InvitationRedeemed": ["address", "address", "address"] + }, + { + "InvitationRevoked": ["address", "address"] + }, + { + "RecordSaleTransaction": ["address", "int"] + } + ] + }, + "functions": [ + { + "arguments": [], + "name": "init", + "payable": false, + "returns": "AffiliationTreasury.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "get_direct_inviter", + "payable": false, + "returns": { + "option": ["address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_percentage", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "get_accumulated_rewards", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_precision", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_percentages", + "payable": false, + "returns": { + "list": ["int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "payout_periods", + "payable": false, + "returns": { + "map": [ + "int", + { + "map": ["address", "int"] + } + ] + }, + "stateful": false + }, + { + "arguments": [], + "name": "unique_invitees", + "payable": false, + "returns": { + "map": ["address", "AffiliationTreasury.unique_invitees_state"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "affiliation_tree", + "payable": false, + "returns": { + "map": ["address", "address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "invitation_codes", + "payable": false, + "returns": { + "map": [ + "address", + { + "tuple": ["address", "int", "bool"] + } + ] + }, + "stateful": false + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "AffiliationTreasury.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_affiliation_tree", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_invitation_code", + "payable": false, + "returns": { + "tuple": ["address", "int", "bool"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_unique_invitee", + "payable": false, + "returns": "AffiliationTreasury.unique_invitees_state", + "stateful": false + }, + { + "arguments": [ + { + "name": "invitation_addresses", + "type": { + "list": ["address"] + } + }, + { + "name": "redemption_fee_cover", + "type": "int" + }, + { + "name": "invitation_amount", + "type": "int" + } + ], + "name": "register_invitation_code", + "payable": true, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "invitation_address", + "type": "address" + } + ], + "name": "revoke_invitation_code", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "invitee_address", + "type": "address" + } + ], + "name": "redeem_invitation_code", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "inviter_address", + "type": "address" + } + ], + "name": "register_invitation", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "buyer", + "type": "address" + }, + { + "name": "transaction_value", + "type": "int" + } + ], + "name": "record_sale_transaction", + "payable": true, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "get_payout_period", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "withdraw", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_child", + "name": "AffiliationTreasury", + "payable": true, + "state": { + "record": [ + { + "name": "payout_periods", + "type": { + "map": [ + "int", + { + "map": ["address", "int"] + } + ] + } + }, + { + "name": "affiliation_tree", + "type": { + "map": ["address", "address"] + } + }, + { + "name": "invitation_codes", + "type": { + "map": [ + "address", + { + "tuple": ["address", "int", "bool"] + } + ] + } + }, + { + "name": "unique_invitees", + "type": { + "map": ["address", "AffiliationTreasury.unique_invitees_state"] + } + } + ] + }, + "typedefs": [ + { + "name": "unique_invitees_state", + "typedef": { + "variant": [ + { + "ThresholdReached": [] + }, + { + "WaitingForInvitations": [ + { + "Set.set": ["address"] + }, + { + "map": ["address", "int"] + } + ] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "address" + } + ], + "name": "mint_protocol_dao_token", + "payable": false, + "returns": "unit", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "ICommunityFactory", + "payable": false, + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Buy": ["int", "int", "int"] + }, + { + "Sell": ["int", "int"] + }, + { + "PriceChange": ["int", "int"] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "beneficiary", + "type": "address" + }, + { + "name": "name", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "bonding_curve", + "type": "BondingCurve" + }, + { + "name": "overwrite_owner", + "type": { + "option": ["address"] + } + }, + { + "name": "affiliation_treasury", + "type": "AffiliationTreasury" + } + ], + "name": "init", + "payable": false, + "returns": "AffiliationBondingCurveTokenSale.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "AffiliationBondingCurveTokenSale.state", + "stateful": false + }, + { + "arguments": [], + "name": "token_contract", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "beneficiary", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "bonding_curve", + "payable": false, + "returns": "BondingCurve", + "stateful": false + }, + { + "arguments": [], + "name": "sale_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + } + ], + "name": "price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + } + ], + "name": "sell_return", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + } + ], + "name": "buy", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + }, + { + "name": "affiliation_rewardee", + "type": "address" + } + ], + "name": "buy_with_affiliation", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + }, + { + "name": "minimal_return_required", + "type": "int" + } + ], + "name": "sell", + "payable": false, + "returns": "int", + "stateful": true + }, + { + "arguments": [ + { + "name": "beneficiary", + "type": "address" + } + ], + "name": "set_beneficiary", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "owner", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": "unit", + "stateful": true + } + ], + "kind": "contract_main", + "name": "AffiliationBondingCurveTokenSale", + "payable": false, + "state": { + "record": [ + { + "name": "token_contract", + "type": "FungibleTokenFull" + }, + { + "name": "bonding_curve", + "type": "BondingCurve" + }, + { + "name": "affiliation_treasury", + "type": "AffiliationTreasury" + }, + { + "name": "owner", + "type": "address" + }, + { + "name": "factory", + "type": "ICommunityFactory" + }, + { + "name": "beneficiary", + "type": "address" + }, + { + "name": "dao_contract", + "type": "ReplaceableDAO" + } + ] + }, + "typedefs": [] + } + } +] diff --git a/examples/bcl-indexer/abis/AffiliationTreasury.aci.json b/examples/bcl-indexer/abis/AffiliationTreasury.aci.json new file mode 100644 index 0000000..cc98277 --- /dev/null +++ b/examples/bcl-indexer/abis/AffiliationTreasury.aci.json @@ -0,0 +1,393 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Option", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Pair", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Set", + "typedefs": [ + { + "name": "set", + "typedef": { + "record": [ + { + "name": "to_map", + "type": { + "map": ["'a", "unit"] + } + } + ] + }, + "vars": [ + { + "name": "'a" + } + ] + } + ] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "UserInvited": ["address", "address"] + }, + { + "RewardAdded": ["address", "int"] + }, + { + "Withdrawn": ["address", "int"] + }, + { + "InvitationRegistered": ["address", "address", "int"] + }, + { + "InvitationRedeemed": ["address", "address", "address"] + }, + { + "InvitationRevoked": ["address", "address"] + }, + { + "RecordSaleTransaction": ["address", "int"] + } + ] + }, + "functions": [ + { + "arguments": [], + "name": "init", + "payable": false, + "returns": "AffiliationTreasury.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "get_direct_inviter", + "payable": false, + "returns": { + "option": ["address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_percentage", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "get_accumulated_rewards", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_precision", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_percentages", + "payable": false, + "returns": { + "list": ["int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "payout_periods", + "payable": false, + "returns": { + "map": [ + "int", + { + "map": ["address", "int"] + } + ] + }, + "stateful": false + }, + { + "arguments": [], + "name": "unique_invitees", + "payable": false, + "returns": { + "map": ["address", "AffiliationTreasury.unique_invitees_state"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "affiliation_tree", + "payable": false, + "returns": { + "map": ["address", "address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "invitation_codes", + "payable": false, + "returns": { + "map": [ + "address", + { + "tuple": ["address", "int", "bool"] + } + ] + }, + "stateful": false + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "AffiliationTreasury.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_affiliation_tree", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_invitation_code", + "payable": false, + "returns": { + "tuple": ["address", "int", "bool"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_unique_invitee", + "payable": false, + "returns": "AffiliationTreasury.unique_invitees_state", + "stateful": false + }, + { + "arguments": [ + { + "name": "invitation_addresses", + "type": { + "list": ["address"] + } + }, + { + "name": "redemption_fee_cover", + "type": "int" + }, + { + "name": "invitation_amount", + "type": "int" + } + ], + "name": "register_invitation_code", + "payable": true, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "invitation_address", + "type": "address" + } + ], + "name": "revoke_invitation_code", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "invitee_address", + "type": "address" + } + ], + "name": "redeem_invitation_code", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "inviter_address", + "type": "address" + } + ], + "name": "register_invitation", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "buyer", + "type": "address" + }, + { + "name": "transaction_value", + "type": "int" + } + ], + "name": "record_sale_transaction", + "payable": true, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "get_payout_period", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "withdraw", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_main", + "name": "AffiliationTreasury", + "payable": true, + "state": { + "record": [ + { + "name": "payout_periods", + "type": { + "map": [ + "int", + { + "map": ["address", "int"] + } + ] + } + }, + { + "name": "affiliation_tree", + "type": { + "map": ["address", "address"] + } + }, + { + "name": "invitation_codes", + "type": { + "map": [ + "address", + { + "tuple": ["address", "int", "bool"] + } + ] + } + }, + { + "name": "unique_invitees", + "type": { + "map": ["address", "AffiliationTreasury.unique_invitees_state"] + } + } + ] + }, + "typedefs": [ + { + "name": "unique_invitees_state", + "typedef": { + "variant": [ + { + "ThresholdReached": [] + }, + { + "WaitingForInvitations": [ + { + "Set.set": ["address"] + }, + { + "map": ["address", "int"] + } + ] + } + ] + }, + "vars": [] + } + ] + } + } +] diff --git a/examples/bcl-indexer/abis/BondingCurve.aci.json b/examples/bcl-indexer/abis/BondingCurve.aci.json new file mode 100644 index 0000000..0023eaf --- /dev/null +++ b/examples/bcl-indexer/abis/BondingCurve.aci.json @@ -0,0 +1,148 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "String", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Frac", + "typedefs": [ + { + "name": "frac", + "typedef": { + "variant": [ + { + "Pos": ["int", "int"] + }, + { + "Zero": [] + }, + { + "Neg": ["int", "int"] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "supported_decimals", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "curve_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "sell_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "calculate_buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "calculate_sell_return", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "sell_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + } + ], + "kind": "contract_main", + "name": "BondingCurve", + "payable": false, + "typedefs": [] + } + } +] diff --git a/examples/bcl-indexer/abis/BondingCurveExponential.aci.json b/examples/bcl-indexer/abis/BondingCurveExponential.aci.json new file mode 100644 index 0000000..050a86c --- /dev/null +++ b/examples/bcl-indexer/abis/BondingCurveExponential.aci.json @@ -0,0 +1,287 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "String", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Frac", + "typedefs": [ + { + "name": "frac", + "typedef": { + "variant": [ + { + "Pos": ["int", "int"] + }, + { + "Zero": [] + }, + { + "Neg": ["int", "int"] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "supported_decimals", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "curve_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "sell_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "calculate_buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "calculate_sell_return", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "sell_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "BondingCurve", + "payable": false, + "typedefs": [] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "get_k", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_initial_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_minimum_count", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_sell_return_percentage", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_sell_return_precision", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "curve_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "supported_decimals", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "total_supply", + "type": "int" + } + ], + "name": "buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "total_supply", + "type": "int" + } + ], + "name": "sell_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "total_supply", + "type": "int" + }, + { + "name": "count", + "type": "int" + } + ], + "name": "calculate_buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "total_supply", + "type": "int" + }, + { + "name": "sell_tokens", + "type": "int" + } + ], + "name": "calculate_sell_return", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "x", + "type": "int" + } + ], + "name": "buy_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + }, + { + "arguments": [ + { + "name": "x", + "type": "int" + } + ], + "name": "sell_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + } + ], + "kind": "contract_main", + "name": "BondingCurveExponential", + "payable": false, + "typedefs": [] + } + } +] diff --git a/examples/bcl-indexer/abis/CommunityFactory.aci.json b/examples/bcl-indexer/abis/CommunityFactory.aci.json new file mode 100644 index 0000000..bdf7dad --- /dev/null +++ b/examples/bcl-indexer/abis/CommunityFactory.aci.json @@ -0,0 +1,2595 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "String", + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Transfer": ["address", "address", "int"] + }, + { + "Allowance": ["address", "address", "int"] + }, + { + "Burn": ["address", "int"] + }, + { + "Mint": ["address", "int"] + }, + { + "Swap": ["address", "int"] + } + ] + }, + "functions": [ + { + "arguments": [], + "name": "aex9_extensions", + "payable": false, + "returns": { + "list": ["string"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "name", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "initial_owner_balance", + "type": { + "option": ["int"] + } + } + ], + "name": "init", + "payable": false, + "returns": "FungibleTokenFull.state", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "FungibleTokenFull.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "total_supply", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "balances", + "payable": false, + "returns": "FungibleTokenFull.balances", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "balance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "swapped", + "payable": false, + "returns": { + "map": ["address", "int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "allowances", + "payable": false, + "returns": "FungibleTokenFull.allowances", + "stateful": false + }, + { + "arguments": [ + { + "name": "allowance_accounts", + "type": "FungibleTokenFull.allowance_accounts" + } + ], + "name": "allowance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + } + ], + "name": "allowance_for_caller", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "create_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value_change", + "type": "int" + } + ], + "name": "change_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + } + ], + "name": "reset_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "value", + "type": "int" + } + ], + "name": "burn", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "mint", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "swap", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "check_swap", + "payable": false, + "returns": "int", + "stateful": true + } + ], + "kind": "contract_child", + "name": "FungibleTokenFull", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "total_supply", + "type": "int" + }, + { + "name": "balances", + "type": "FungibleTokenFull.balances" + }, + { + "name": "meta_info", + "type": "FungibleTokenFull.meta_info" + }, + { + "name": "allowances", + "type": "FungibleTokenFull.allowances" + }, + { + "name": "swapped", + "type": { + "map": ["address", "int"] + } + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "record": [ + { + "name": "name", + "type": "string" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + } + ] + }, + "vars": [] + }, + { + "name": "allowance_accounts", + "typedef": { + "record": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "for_account", + "type": "address" + } + ] + }, + "vars": [] + }, + { + "name": "balances", + "typedef": { + "map": ["address", "int"] + }, + "vars": [] + }, + { + "name": "allowances", + "typedef": { + "map": ["FungibleTokenFull.allowance_accounts", "int"] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "token_contract", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "sale_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "address" + } + ], + "name": "buy_with_affiliation", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + } + ], + "name": "set_beneficiary", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [], + "name": "beneficiary", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "TokenSale", + "payable": false, + "typedefs": [] + } + }, + { + "namespace": { + "name": "Option", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Pair", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Set", + "typedefs": [ + { + "name": "set", + "typedef": { + "record": [ + { + "name": "to_map", + "type": { + "map": ["'a", "unit"] + } + } + ] + }, + "vars": [ + { + "name": "'a" + } + ] + } + ] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "ChangeMinimumTokenThreshold": ["int"] + }, + { + "AddModerator": ["address"] + }, + { + "DeleteModerator": ["address"] + }, + { + "MuteUserId": ["string"] + }, + { + "UnmuteUserId": ["string"] + }, + { + "SetOwner": ["address"] + }, + { + "ChangedMetaInfo": [] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "initial_moderator", + "type": "address" + }, + { + "name": "minimum_token_threshold", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "init", + "payable": false, + "returns": "CommunityManagement.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "CommunityManagement.state", + "stateful": false + }, + { + "arguments": [], + "name": "moderator_accounts", + "payable": false, + "returns": { + "Set.set": ["address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "muted_user_ids", + "payable": false, + "returns": { + "Set.set": ["string"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "minimum_token_threshold", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "CommunityManagement.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "minimum_token_threshold", + "type": "int" + } + ], + "name": "change_minimum_token_threshold", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "moderator", + "type": "address" + } + ], + "name": "add_moderator", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "moderator", + "type": "address" + } + ], + "name": "delete_moderator", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "user_id", + "type": "string" + } + ], + "name": "mute_user_id", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "user_id", + "type": "string" + } + ], + "name": "unmute_user_id", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "change_meta_info", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "owner", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_child", + "name": "CommunityManagement", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "minimum_token_threshold", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "moderator_accounts", + "type": { + "Set.set": ["address"] + } + }, + { + "name": "muted_user_ids", + "type": { + "Set.set": ["string"] + } + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "map": ["string", "string"] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "is_dao", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "get_community_management", + "payable": false, + "returns": { + "option": ["CommunityManagement"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "record_sale_transaction", + "payable": true, + "returns": "unit", + "stateful": true + } + ], + "kind": "contract_interface", + "name": "ReplaceableDAO", + "payable": false, + "typedefs": [] + } + }, + { + "namespace": { + "name": "VoteSubjects", + "typedefs": [ + { + "name": "subject", + "typedef": { + "variant": [ + { + "VotePayout": ["address"] + }, + { + "VotePayoutAmount": ["address", "int"] + }, + { + "ChangeDAO": ["address"] + }, + { + "ChangeMetaInfo": [ + { + "map": ["string", "string"] + } + ] + }, + { + "ChangeMinimumTokenThreshold": ["int"] + }, + { + "AddModerator": ["address"] + }, + { + "DeleteModerator": ["address"] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Vote": ["address", "DAOVote.vote_option", "DAOVote.amount"] + }, + { + "RevokeVote": ["address", "DAOVote.vote_option", "DAOVote.amount"] + }, + { + "Withdraw": ["address", "DAOVote.amount"] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "metadata", + "type": "DAOVote.metadata" + }, + { + "name": "token", + "type": "FungibleTokenFull" + }, + { + "name": "author", + "type": "address" + } + ], + "name": "init", + "payable": false, + "returns": "DAOVote.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "option", + "type": "DAOVote.vote_option" + }, + { + "name": "amount", + "type": "DAOVote.amount" + } + ], + "name": "vote", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "revoke_vote", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "withdraw", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "DAOVote.state", + "stateful": false + }, + { + "arguments": [], + "name": "close_height", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "metadata", + "payable": false, + "returns": "DAOVote.metadata", + "stateful": false + }, + { + "arguments": [], + "name": "subject", + "payable": false, + "returns": "VoteSubjects.subject", + "stateful": false + }, + { + "arguments": [], + "name": "token", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "vote_accounts", + "payable": false, + "returns": "DAOVote.vote_accounts", + "stateful": false + }, + { + "arguments": [], + "name": "current_vote_state", + "payable": false, + "returns": "DAOVote.vote_state", + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "has_voted", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "is_closed", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "has_withdrawn", + "payable": false, + "returns": { + "option": ["bool"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "final_vote_state", + "payable": false, + "returns": { + "option": ["DAOVote.vote_state"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "voted_option", + "payable": false, + "returns": { + "option": ["DAOVote.vote_option"] + }, + "stateful": false + } + ], + "kind": "contract_child", + "name": "DAOVote", + "payable": false, + "state": { + "record": [ + { + "name": "metadata", + "type": "DAOVote.metadata" + }, + { + "name": "close_height", + "type": "int" + }, + { + "name": "create_height", + "type": "int" + }, + { + "name": "vote_state", + "type": "DAOVote.vote_state" + }, + { + "name": "vote_accounts", + "type": "DAOVote.vote_accounts" + }, + { + "name": "token", + "type": "FungibleTokenFull" + }, + { + "name": "author", + "type": "address" + } + ] + }, + "typedefs": [ + { + "name": "vote_option", + "typedef": "bool", + "vars": [] + }, + { + "name": "amount", + "typedef": "int", + "vars": [] + }, + { + "name": "vote_state", + "typedef": { + "map": ["DAOVote.vote_option", "DAOVote.amount"] + }, + "vars": [] + }, + { + "name": "vote_accounts", + "typedef": { + "map": [ + "address", + { + "tuple": ["DAOVote.amount", "DAOVote.vote_option", "bool"] + } + ] + }, + "vars": [] + }, + { + "name": "metadata", + "typedef": { + "record": [ + { + "name": "subject", + "type": "VoteSubjects.subject" + }, + { + "name": "description", + "type": "string" + }, + { + "name": "link", + "type": "string" + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [ + { + "name": "_1", + "type": "TokenSale" + } + ], + "name": "get_community_management", + "payable": false, + "returns": "CommunityManagement", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "Factory", + "payable": false, + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "VoteAdded": ["DAOVote", "int"] + }, + { + "AppliedVoteSubject": ["DAOVote", "int"] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "token_sale", + "type": { + "option": ["TokenSale"] + } + }, + { + "name": "factory_address", + "type": "address" + } + ], + "name": "init", + "payable": false, + "returns": "DAO.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_token", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "votes", + "payable": false, + "returns": "DAO.votes", + "stateful": false + }, + { + "arguments": [], + "name": "vote_timeout", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "factory", + "payable": false, + "returns": "Factory", + "stateful": false + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "DAO.state", + "stateful": false + }, + { + "arguments": [], + "name": "get_token_sale", + "payable": false, + "returns": "TokenSale", + "stateful": false + }, + { + "arguments": [ + { + "name": "buyer", + "type": "address" + }, + { + "name": "buy_price", + "type": "int" + } + ], + "name": "record_sale_transaction", + "payable": true, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "get_community_management", + "payable": false, + "returns": { + "option": ["CommunityManagement"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "is_dao", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "token_sale", + "type": "TokenSale" + } + ], + "name": "set_token_sale", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "metadata", + "type": "DAOVote.metadata" + } + ], + "name": "add_vote", + "payable": true, + "returns": { + "tuple": ["int", "DAOVote"] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "vote_seq_id", + "type": "int" + } + ], + "name": "apply_vote_subject", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_child", + "name": "DAO", + "payable": true, + "state": { + "record": [ + { + "name": "token_sale", + "type": { + "option": ["TokenSale"] + } + }, + { + "name": "votes", + "type": "DAO.votes" + }, + { + "name": "vote_timeout", + "type": "int" + }, + { + "name": "factory", + "type": "Factory" + } + ] + }, + "typedefs": [ + { + "name": "votes", + "typedef": { + "map": [ + "int", + { + "tuple": ["bool", "DAOVote"] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "namespace": { + "name": "Frac", + "typedefs": [ + { + "name": "frac", + "typedef": { + "variant": [ + { + "Pos": ["int", "int"] + }, + { + "Zero": [] + }, + { + "Neg": ["int", "int"] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "supported_decimals", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "curve_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "sell_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "calculate_buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "calculate_sell_return", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "sell_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "BondingCurve", + "payable": false, + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "UserInvited": ["address", "address"] + }, + { + "RewardAdded": ["address", "int"] + }, + { + "Withdrawn": ["address", "int"] + }, + { + "InvitationRegistered": ["address", "address", "int"] + }, + { + "InvitationRedeemed": ["address", "address", "address"] + }, + { + "InvitationRevoked": ["address", "address"] + }, + { + "RecordSaleTransaction": ["address", "int"] + } + ] + }, + "functions": [ + { + "arguments": [], + "name": "init", + "payable": false, + "returns": "AffiliationTreasury.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "get_direct_inviter", + "payable": false, + "returns": { + "option": ["address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_percentage", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "get_accumulated_rewards", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_precision", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_affiliation_fee_percentages", + "payable": false, + "returns": { + "list": ["int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "payout_periods", + "payable": false, + "returns": { + "map": [ + "int", + { + "map": ["address", "int"] + } + ] + }, + "stateful": false + }, + { + "arguments": [], + "name": "unique_invitees", + "payable": false, + "returns": { + "map": ["address", "AffiliationTreasury.unique_invitees_state"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "affiliation_tree", + "payable": false, + "returns": { + "map": ["address", "address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "invitation_codes", + "payable": false, + "returns": { + "map": [ + "address", + { + "tuple": ["address", "int", "bool"] + } + ] + }, + "stateful": false + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "AffiliationTreasury.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_affiliation_tree", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_invitation_code", + "payable": false, + "returns": { + "tuple": ["address", "int", "bool"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "address", + "type": "address" + } + ], + "name": "get_unique_invitee", + "payable": false, + "returns": "AffiliationTreasury.unique_invitees_state", + "stateful": false + }, + { + "arguments": [ + { + "name": "invitation_addresses", + "type": { + "list": ["address"] + } + }, + { + "name": "redemption_fee_cover", + "type": "int" + }, + { + "name": "invitation_amount", + "type": "int" + } + ], + "name": "register_invitation_code", + "payable": true, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "invitation_address", + "type": "address" + } + ], + "name": "revoke_invitation_code", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "invitee_address", + "type": "address" + } + ], + "name": "redeem_invitation_code", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "inviter_address", + "type": "address" + } + ], + "name": "register_invitation", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "buyer", + "type": "address" + }, + { + "name": "transaction_value", + "type": "int" + } + ], + "name": "record_sale_transaction", + "payable": true, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "get_payout_period", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "withdraw", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_child", + "name": "AffiliationTreasury", + "payable": true, + "state": { + "record": [ + { + "name": "payout_periods", + "type": { + "map": [ + "int", + { + "map": ["address", "int"] + } + ] + } + }, + { + "name": "affiliation_tree", + "type": { + "map": ["address", "address"] + } + }, + { + "name": "invitation_codes", + "type": { + "map": [ + "address", + { + "tuple": ["address", "int", "bool"] + } + ] + } + }, + { + "name": "unique_invitees", + "type": { + "map": ["address", "AffiliationTreasury.unique_invitees_state"] + } + } + ] + }, + "typedefs": [ + { + "name": "unique_invitees_state", + "typedef": { + "variant": [ + { + "ThresholdReached": [] + }, + { + "WaitingForInvitations": [ + { + "Set.set": ["address"] + }, + { + "map": ["address", "int"] + } + ] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "address" + } + ], + "name": "mint_protocol_dao_token", + "payable": false, + "returns": "unit", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "ICommunityFactory", + "payable": false, + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Buy": ["int", "int", "int"] + }, + { + "Sell": ["int", "int"] + }, + { + "PriceChange": ["int", "int"] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "beneficiary", + "type": "address" + }, + { + "name": "name", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "bonding_curve", + "type": "BondingCurve" + }, + { + "name": "overwrite_owner", + "type": { + "option": ["address"] + } + }, + { + "name": "affiliation_treasury", + "type": "AffiliationTreasury" + } + ], + "name": "init", + "payable": false, + "returns": "AffiliationBondingCurveTokenSale.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "AffiliationBondingCurveTokenSale.state", + "stateful": false + }, + { + "arguments": [], + "name": "token_contract", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "beneficiary", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "bonding_curve", + "payable": false, + "returns": "BondingCurve", + "stateful": false + }, + { + "arguments": [], + "name": "sale_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + } + ], + "name": "price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + } + ], + "name": "sell_return", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + } + ], + "name": "buy", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + }, + { + "name": "affiliation_rewardee", + "type": "address" + } + ], + "name": "buy_with_affiliation", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "count", + "type": "int" + }, + { + "name": "minimal_return_required", + "type": "int" + } + ], + "name": "sell", + "payable": false, + "returns": "int", + "stateful": true + }, + { + "arguments": [ + { + "name": "beneficiary", + "type": "address" + } + ], + "name": "set_beneficiary", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "owner", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": "unit", + "stateful": true + } + ], + "kind": "contract_child", + "name": "AffiliationBondingCurveTokenSale", + "payable": false, + "state": { + "record": [ + { + "name": "token_contract", + "type": "FungibleTokenFull" + }, + { + "name": "bonding_curve", + "type": "BondingCurve" + }, + { + "name": "affiliation_treasury", + "type": "AffiliationTreasury" + }, + { + "name": "owner", + "type": "address" + }, + { + "name": "factory", + "type": "ICommunityFactory" + }, + { + "name": "beneficiary", + "type": "address" + }, + { + "name": "dao_contract", + "type": "ReplaceableDAO" + } + ] + }, + "typedefs": [] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "get_k", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_initial_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_minimum_count", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_sell_return_percentage", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "get_sell_return_precision", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "curve_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "supported_decimals", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "total_supply", + "type": "int" + } + ], + "name": "buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "total_supply", + "type": "int" + } + ], + "name": "sell_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "total_supply", + "type": "int" + }, + { + "name": "count", + "type": "int" + } + ], + "name": "calculate_buy_price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "total_supply", + "type": "int" + }, + { + "name": "sell_tokens", + "type": "int" + } + ], + "name": "calculate_sell_return", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "x", + "type": "int" + } + ], + "name": "buy_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + }, + { + "arguments": [ + { + "name": "x", + "type": "int" + } + ], + "name": "sell_curve", + "payable": false, + "returns": "Frac.frac", + "stateful": false + } + ], + "kind": "contract_child", + "name": "BondingCurveExponential", + "payable": false, + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "CreateCommunity": [ + "string", + "DAO", + "TokenSale", + "CommunityManagement" + ] + }, + { + "CreateCollection": ["string", "address"] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "protocol_token_name", + "type": "string" + } + ], + "name": "init", + "payable": false, + "returns": "CommunityFactory.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "CommunityFactory.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "collection_name", + "type": "string" + } + ], + "name": "allowed_name_length", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "collection_name", + "type": "string" + } + ], + "name": "allowed_name_chars", + "payable": false, + "returns": { + "list": ["CommunityFactory.allowedNameChars"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "collection_name", + "type": "string" + } + ], + "name": "token_sale_registry", + "payable": false, + "returns": "CommunityFactory.token_sale_registry", + "stateful": false + }, + { + "arguments": [], + "name": "community_management", + "payable": false, + "returns": "CommunityFactory.community_management", + "stateful": false + }, + { + "arguments": [], + "name": "affiliation_treasury", + "payable": false, + "returns": "AffiliationTreasury", + "stateful": false + }, + { + "arguments": [], + "name": "fee_percentage", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "fee_precision", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "bonding_curve", + "payable": false, + "returns": "BondingCurve", + "stateful": false + }, + { + "arguments": [ + { + "name": "token_sale", + "type": "TokenSale" + } + ], + "name": "get_community_management", + "payable": false, + "returns": "CommunityManagement", + "stateful": false + }, + { + "arguments": [ + { + "name": "collection_name", + "type": "string" + }, + { + "name": "name", + "type": "string" + } + ], + "name": "get_token_sale", + "payable": false, + "returns": "TokenSale", + "stateful": false + }, + { + "arguments": [ + { + "name": "collection_name", + "type": "string" + }, + { + "name": "name", + "type": "string" + } + ], + "name": "token_contract", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [ + { + "name": "collection_name", + "type": "string" + }, + { + "name": "name", + "type": "string" + } + ], + "name": "has_community", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "factory_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "protocol_dao_token", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "buy_value", + "type": "int" + }, + { + "name": "receiver", + "type": "address" + } + ], + "name": "mint_protocol_dao_token", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "collection_name", + "type": "string" + }, + { + "name": "allowed_name_length", + "type": "int" + }, + { + "name": "allowed_name_chars", + "type": { + "list": ["CommunityFactory.allowedNameChars"] + } + } + ], + "name": "create_collection", + "payable": true, + "returns": "string", + "stateful": true + }, + { + "arguments": [ + { + "name": "collection_name", + "type": "string" + }, + { + "name": "name", + "type": "string" + }, + { + "name": "initial_buy_count", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "create_community", + "payable": true, + "returns": { + "tuple": ["DAO", "TokenSale", "CommunityManagement"] + }, + "stateful": true + } + ], + "kind": "contract_main", + "name": "CommunityFactory", + "payable": false, + "state": { + "record": [ + { + "name": "collection_registry", + "type": "CommunityFactory.collection_registry" + }, + { + "name": "known_token_sales", + "type": "CommunityFactory.known_token_sales" + }, + { + "name": "community_management", + "type": "CommunityFactory.community_management" + }, + { + "name": "affiliation_treasury", + "type": "AffiliationTreasury" + }, + { + "name": "bonding_curve", + "type": "BondingCurve" + }, + { + "name": "protocol_dao_token", + "type": "FungibleTokenFull" + } + ] + }, + "typedefs": [ + { + "name": "token_sale_registry", + "typedef": { + "map": ["string", "TokenSale"] + }, + "vars": [] + }, + { + "name": "known_token_sales", + "typedef": { + "Set.set": ["address"] + }, + "vars": [] + }, + { + "name": "community_management", + "typedef": { + "map": ["TokenSale", "CommunityManagement"] + }, + "vars": [] + }, + { + "name": "collection_data", + "typedef": { + "record": [ + { + "name": "allowed_name_chars", + "type": { + "list": ["CommunityFactory.allowedNameChars"] + } + }, + { + "name": "allowed_name_length", + "type": "int" + }, + { + "name": "token_sale_registry", + "type": "CommunityFactory.token_sale_registry" + } + ] + }, + "vars": [] + }, + { + "name": "collection_registry", + "typedef": { + "map": ["string", "CommunityFactory.collection_data"] + }, + "vars": [] + }, + { + "name": "allowedNameChars", + "typedef": { + "variant": [ + { + "SingleChar": ["int"] + }, + { + "CharRangeFromTo": ["int", "int"] + } + ] + }, + "vars": [] + } + ] + } + } +] diff --git a/examples/bcl-indexer/abis/CommunityManagement.aci.json b/examples/bcl-indexer/abis/CommunityManagement.aci.json new file mode 100644 index 0000000..93910b2 --- /dev/null +++ b/examples/bcl-indexer/abis/CommunityManagement.aci.json @@ -0,0 +1,301 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Option", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Pair", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Set", + "typedefs": [ + { + "name": "set", + "typedef": { + "record": [ + { + "name": "to_map", + "type": { + "map": ["'a", "unit"] + } + } + ] + }, + "vars": [ + { + "name": "'a" + } + ] + } + ] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "ChangeMinimumTokenThreshold": ["int"] + }, + { + "AddModerator": ["address"] + }, + { + "DeleteModerator": ["address"] + }, + { + "MuteUserId": ["string"] + }, + { + "UnmuteUserId": ["string"] + }, + { + "SetOwner": ["address"] + }, + { + "ChangedMetaInfo": [] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "initial_moderator", + "type": "address" + }, + { + "name": "minimum_token_threshold", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "init", + "payable": false, + "returns": "CommunityManagement.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "CommunityManagement.state", + "stateful": false + }, + { + "arguments": [], + "name": "moderator_accounts", + "payable": false, + "returns": { + "Set.set": ["address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "muted_user_ids", + "payable": false, + "returns": { + "Set.set": ["string"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "minimum_token_threshold", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "CommunityManagement.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "minimum_token_threshold", + "type": "int" + } + ], + "name": "change_minimum_token_threshold", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "moderator", + "type": "address" + } + ], + "name": "add_moderator", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "moderator", + "type": "address" + } + ], + "name": "delete_moderator", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "user_id", + "type": "string" + } + ], + "name": "mute_user_id", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "user_id", + "type": "string" + } + ], + "name": "unmute_user_id", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "change_meta_info", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "owner", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_main", + "name": "CommunityManagement", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "minimum_token_threshold", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "moderator_accounts", + "type": { + "Set.set": ["address"] + } + }, + { + "name": "muted_user_ids", + "type": { + "Set.set": ["string"] + } + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "map": ["string", "string"] + }, + "vars": [] + } + ] + } + } +] diff --git a/examples/bcl-indexer/abis/DAO.aci.json b/examples/bcl-indexer/abis/DAO.aci.json new file mode 100644 index 0000000..5dd1475 --- /dev/null +++ b/examples/bcl-indexer/abis/DAO.aci.json @@ -0,0 +1,1365 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "String", + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Transfer": ["address", "address", "int"] + }, + { + "Allowance": ["address", "address", "int"] + }, + { + "Burn": ["address", "int"] + }, + { + "Mint": ["address", "int"] + }, + { + "Swap": ["address", "int"] + } + ] + }, + "functions": [ + { + "arguments": [], + "name": "aex9_extensions", + "payable": false, + "returns": { + "list": ["string"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "name", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "initial_owner_balance", + "type": { + "option": ["int"] + } + } + ], + "name": "init", + "payable": false, + "returns": "FungibleTokenFull.state", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "FungibleTokenFull.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "total_supply", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "balances", + "payable": false, + "returns": "FungibleTokenFull.balances", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "balance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "swapped", + "payable": false, + "returns": { + "map": ["address", "int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "allowances", + "payable": false, + "returns": "FungibleTokenFull.allowances", + "stateful": false + }, + { + "arguments": [ + { + "name": "allowance_accounts", + "type": "FungibleTokenFull.allowance_accounts" + } + ], + "name": "allowance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + } + ], + "name": "allowance_for_caller", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "create_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value_change", + "type": "int" + } + ], + "name": "change_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + } + ], + "name": "reset_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "value", + "type": "int" + } + ], + "name": "burn", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "mint", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "swap", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "check_swap", + "payable": false, + "returns": "int", + "stateful": true + } + ], + "kind": "contract_child", + "name": "FungibleTokenFull", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "total_supply", + "type": "int" + }, + { + "name": "balances", + "type": "FungibleTokenFull.balances" + }, + { + "name": "meta_info", + "type": "FungibleTokenFull.meta_info" + }, + { + "name": "allowances", + "type": "FungibleTokenFull.allowances" + }, + { + "name": "swapped", + "type": { + "map": ["address", "int"] + } + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "record": [ + { + "name": "name", + "type": "string" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + } + ] + }, + "vars": [] + }, + { + "name": "allowance_accounts", + "typedef": { + "record": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "for_account", + "type": "address" + } + ] + }, + "vars": [] + }, + { + "name": "balances", + "typedef": { + "map": ["address", "int"] + }, + "vars": [] + }, + { + "name": "allowances", + "typedef": { + "map": ["FungibleTokenFull.allowance_accounts", "int"] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "token_contract", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "sale_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "address" + } + ], + "name": "buy_with_affiliation", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + } + ], + "name": "set_beneficiary", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [], + "name": "beneficiary", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "TokenSale", + "payable": false, + "typedefs": [] + } + }, + { + "namespace": { + "name": "Option", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Pair", + "typedefs": [] + } + }, + { + "namespace": { + "name": "Set", + "typedefs": [ + { + "name": "set", + "typedef": { + "record": [ + { + "name": "to_map", + "type": { + "map": ["'a", "unit"] + } + } + ] + }, + "vars": [ + { + "name": "'a" + } + ] + } + ] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "ChangeMinimumTokenThreshold": ["int"] + }, + { + "AddModerator": ["address"] + }, + { + "DeleteModerator": ["address"] + }, + { + "MuteUserId": ["string"] + }, + { + "UnmuteUserId": ["string"] + }, + { + "SetOwner": ["address"] + }, + { + "ChangedMetaInfo": [] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "initial_moderator", + "type": "address" + }, + { + "name": "minimum_token_threshold", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "init", + "payable": false, + "returns": "CommunityManagement.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "CommunityManagement.state", + "stateful": false + }, + { + "arguments": [], + "name": "moderator_accounts", + "payable": false, + "returns": { + "Set.set": ["address"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "muted_user_ids", + "payable": false, + "returns": { + "Set.set": ["string"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "minimum_token_threshold", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "CommunityManagement.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "minimum_token_threshold", + "type": "int" + } + ], + "name": "change_minimum_token_threshold", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "moderator", + "type": "address" + } + ], + "name": "add_moderator", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "moderator", + "type": "address" + } + ], + "name": "delete_moderator", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "user_id", + "type": "string" + } + ], + "name": "mute_user_id", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "user_id", + "type": "string" + } + ], + "name": "unmute_user_id", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ], + "name": "change_meta_info", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "owner", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_child", + "name": "CommunityManagement", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "minimum_token_threshold", + "type": "int" + }, + { + "name": "is_private", + "type": "bool" + }, + { + "name": "moderator_accounts", + "type": { + "Set.set": ["address"] + } + }, + { + "name": "muted_user_ids", + "type": { + "Set.set": ["string"] + } + }, + { + "name": "meta_info", + "type": "CommunityManagement.meta_info" + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "map": ["string", "string"] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [], + "name": "is_dao", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "get_community_management", + "payable": false, + "returns": { + "option": ["CommunityManagement"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + }, + { + "name": "_2", + "type": "int" + } + ], + "name": "record_sale_transaction", + "payable": true, + "returns": "unit", + "stateful": true + } + ], + "kind": "contract_interface", + "name": "ReplaceableDAO", + "payable": false, + "typedefs": [] + } + }, + { + "namespace": { + "name": "VoteSubjects", + "typedefs": [ + { + "name": "subject", + "typedef": { + "variant": [ + { + "VotePayout": ["address"] + }, + { + "VotePayoutAmount": ["address", "int"] + }, + { + "ChangeDAO": ["address"] + }, + { + "ChangeMetaInfo": [ + { + "map": ["string", "string"] + } + ] + }, + { + "ChangeMinimumTokenThreshold": ["int"] + }, + { + "AddModerator": ["address"] + }, + { + "DeleteModerator": ["address"] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Vote": ["address", "DAOVote.vote_option", "DAOVote.amount"] + }, + { + "RevokeVote": ["address", "DAOVote.vote_option", "DAOVote.amount"] + }, + { + "Withdraw": ["address", "DAOVote.amount"] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "metadata", + "type": "DAOVote.metadata" + }, + { + "name": "token", + "type": "FungibleTokenFull" + }, + { + "name": "author", + "type": "address" + } + ], + "name": "init", + "payable": false, + "returns": "DAOVote.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "option", + "type": "DAOVote.vote_option" + }, + { + "name": "amount", + "type": "DAOVote.amount" + } + ], + "name": "vote", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "revoke_vote", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "withdraw", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "DAOVote.state", + "stateful": false + }, + { + "arguments": [], + "name": "close_height", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "metadata", + "payable": false, + "returns": "DAOVote.metadata", + "stateful": false + }, + { + "arguments": [], + "name": "subject", + "payable": false, + "returns": "VoteSubjects.subject", + "stateful": false + }, + { + "arguments": [], + "name": "token", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "vote_accounts", + "payable": false, + "returns": "DAOVote.vote_accounts", + "stateful": false + }, + { + "arguments": [], + "name": "current_vote_state", + "payable": false, + "returns": "DAOVote.vote_state", + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "has_voted", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "is_closed", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "has_withdrawn", + "payable": false, + "returns": { + "option": ["bool"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "final_vote_state", + "payable": false, + "returns": { + "option": ["DAOVote.vote_state"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "voted_option", + "payable": false, + "returns": { + "option": ["DAOVote.vote_option"] + }, + "stateful": false + } + ], + "kind": "contract_child", + "name": "DAOVote", + "payable": false, + "state": { + "record": [ + { + "name": "metadata", + "type": "DAOVote.metadata" + }, + { + "name": "close_height", + "type": "int" + }, + { + "name": "create_height", + "type": "int" + }, + { + "name": "vote_state", + "type": "DAOVote.vote_state" + }, + { + "name": "vote_accounts", + "type": "DAOVote.vote_accounts" + }, + { + "name": "token", + "type": "FungibleTokenFull" + }, + { + "name": "author", + "type": "address" + } + ] + }, + "typedefs": [ + { + "name": "vote_option", + "typedef": "bool", + "vars": [] + }, + { + "name": "amount", + "typedef": "int", + "vars": [] + }, + { + "name": "vote_state", + "typedef": { + "map": ["DAOVote.vote_option", "DAOVote.amount"] + }, + "vars": [] + }, + { + "name": "vote_accounts", + "typedef": { + "map": [ + "address", + { + "tuple": ["DAOVote.amount", "DAOVote.vote_option", "bool"] + } + ] + }, + "vars": [] + }, + { + "name": "metadata", + "typedef": { + "record": [ + { + "name": "subject", + "type": "VoteSubjects.subject" + }, + { + "name": "description", + "type": "string" + }, + { + "name": "link", + "type": "string" + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [ + { + "name": "_1", + "type": "TokenSale" + } + ], + "name": "get_community_management", + "payable": false, + "returns": "CommunityManagement", + "stateful": false + } + ], + "kind": "contract_interface", + "name": "Factory", + "payable": false, + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "VoteAdded": ["DAOVote", "int"] + }, + { + "AppliedVoteSubject": ["DAOVote", "int"] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "token_sale", + "type": { + "option": ["TokenSale"] + } + }, + { + "name": "factory_address", + "type": "address" + } + ], + "name": "init", + "payable": false, + "returns": "DAO.state", + "stateful": true + }, + { + "arguments": [], + "name": "get_token", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "votes", + "payable": false, + "returns": "DAO.votes", + "stateful": false + }, + { + "arguments": [], + "name": "vote_timeout", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "factory", + "payable": false, + "returns": "Factory", + "stateful": false + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "DAO.state", + "stateful": false + }, + { + "arguments": [], + "name": "get_token_sale", + "payable": false, + "returns": "TokenSale", + "stateful": false + }, + { + "arguments": [ + { + "name": "buyer", + "type": "address" + }, + { + "name": "buy_price", + "type": "int" + } + ], + "name": "record_sale_transaction", + "payable": true, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "get_community_management", + "payable": false, + "returns": { + "option": ["CommunityManagement"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "is_dao", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "token_sale", + "type": "TokenSale" + } + ], + "name": "set_token_sale", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "metadata", + "type": "DAOVote.metadata" + } + ], + "name": "add_vote", + "payable": true, + "returns": { + "tuple": ["int", "DAOVote"] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "vote_seq_id", + "type": "int" + } + ], + "name": "apply_vote_subject", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + } + ], + "kind": "contract_main", + "name": "DAO", + "payable": true, + "state": { + "record": [ + { + "name": "token_sale", + "type": { + "option": ["TokenSale"] + } + }, + { + "name": "votes", + "type": "DAO.votes" + }, + { + "name": "vote_timeout", + "type": "int" + }, + { + "name": "factory", + "type": "Factory" + } + ] + }, + "typedefs": [ + { + "name": "votes", + "typedef": { + "map": [ + "int", + { + "tuple": ["bool", "DAOVote"] + } + ] + }, + "vars": [] + } + ] + } + } +] diff --git a/examples/bcl-indexer/abis/DAOVote.aci.json b/examples/bcl-indexer/abis/DAOVote.aci.json new file mode 100644 index 0000000..d3bd912 --- /dev/null +++ b/examples/bcl-indexer/abis/DAOVote.aci.json @@ -0,0 +1,707 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "String", + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Transfer": ["address", "address", "int"] + }, + { + "Allowance": ["address", "address", "int"] + }, + { + "Burn": ["address", "int"] + }, + { + "Mint": ["address", "int"] + }, + { + "Swap": ["address", "int"] + } + ] + }, + "functions": [ + { + "arguments": [], + "name": "aex9_extensions", + "payable": false, + "returns": { + "list": ["string"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "name", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "initial_owner_balance", + "type": { + "option": ["int"] + } + } + ], + "name": "init", + "payable": false, + "returns": "FungibleTokenFull.state", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "FungibleTokenFull.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "total_supply", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "balances", + "payable": false, + "returns": "FungibleTokenFull.balances", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "balance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "swapped", + "payable": false, + "returns": { + "map": ["address", "int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "allowances", + "payable": false, + "returns": "FungibleTokenFull.allowances", + "stateful": false + }, + { + "arguments": [ + { + "name": "allowance_accounts", + "type": "FungibleTokenFull.allowance_accounts" + } + ], + "name": "allowance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + } + ], + "name": "allowance_for_caller", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "create_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value_change", + "type": "int" + } + ], + "name": "change_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + } + ], + "name": "reset_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "value", + "type": "int" + } + ], + "name": "burn", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "mint", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "swap", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "check_swap", + "payable": false, + "returns": "int", + "stateful": true + } + ], + "kind": "contract_child", + "name": "FungibleTokenFull", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "total_supply", + "type": "int" + }, + { + "name": "balances", + "type": "FungibleTokenFull.balances" + }, + { + "name": "meta_info", + "type": "FungibleTokenFull.meta_info" + }, + { + "name": "allowances", + "type": "FungibleTokenFull.allowances" + }, + { + "name": "swapped", + "type": { + "map": ["address", "int"] + } + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "record": [ + { + "name": "name", + "type": "string" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + } + ] + }, + "vars": [] + }, + { + "name": "allowance_accounts", + "typedef": { + "record": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "for_account", + "type": "address" + } + ] + }, + "vars": [] + }, + { + "name": "balances", + "typedef": { + "map": ["address", "int"] + }, + "vars": [] + }, + { + "name": "allowances", + "typedef": { + "map": ["FungibleTokenFull.allowance_accounts", "int"] + }, + "vars": [] + } + ] + } + }, + { + "namespace": { + "name": "VoteSubjects", + "typedefs": [ + { + "name": "subject", + "typedef": { + "variant": [ + { + "VotePayout": ["address"] + }, + { + "VotePayoutAmount": ["address", "int"] + }, + { + "ChangeDAO": ["address"] + }, + { + "ChangeMetaInfo": [ + { + "map": ["string", "string"] + } + ] + }, + { + "ChangeMinimumTokenThreshold": ["int"] + }, + { + "AddModerator": ["address"] + }, + { + "DeleteModerator": ["address"] + } + ] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Vote": ["address", "DAOVote.vote_option", "DAOVote.amount"] + }, + { + "RevokeVote": ["address", "DAOVote.vote_option", "DAOVote.amount"] + }, + { + "Withdraw": ["address", "DAOVote.amount"] + } + ] + }, + "functions": [ + { + "arguments": [ + { + "name": "metadata", + "type": "DAOVote.metadata" + }, + { + "name": "token", + "type": "FungibleTokenFull" + }, + { + "name": "author", + "type": "address" + } + ], + "name": "init", + "payable": false, + "returns": "DAOVote.state", + "stateful": false + }, + { + "arguments": [ + { + "name": "option", + "type": "DAOVote.vote_option" + }, + { + "name": "amount", + "type": "DAOVote.amount" + } + ], + "name": "vote", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "revoke_vote", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "withdraw", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "get_state", + "payable": false, + "returns": "DAOVote.state", + "stateful": false + }, + { + "arguments": [], + "name": "close_height", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "metadata", + "payable": false, + "returns": "DAOVote.metadata", + "stateful": false + }, + { + "arguments": [], + "name": "subject", + "payable": false, + "returns": "VoteSubjects.subject", + "stateful": false + }, + { + "arguments": [], + "name": "token", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "vote_accounts", + "payable": false, + "returns": "DAOVote.vote_accounts", + "stateful": false + }, + { + "arguments": [], + "name": "current_vote_state", + "payable": false, + "returns": "DAOVote.vote_state", + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "has_voted", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "is_closed", + "payable": false, + "returns": "bool", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "has_withdrawn", + "payable": false, + "returns": { + "option": ["bool"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "final_vote_state", + "payable": false, + "returns": { + "option": ["DAOVote.vote_state"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "voter", + "type": "address" + } + ], + "name": "voted_option", + "payable": false, + "returns": { + "option": ["DAOVote.vote_option"] + }, + "stateful": false + } + ], + "kind": "contract_main", + "name": "DAOVote", + "payable": false, + "state": { + "record": [ + { + "name": "metadata", + "type": "DAOVote.metadata" + }, + { + "name": "close_height", + "type": "int" + }, + { + "name": "create_height", + "type": "int" + }, + { + "name": "vote_state", + "type": "DAOVote.vote_state" + }, + { + "name": "vote_accounts", + "type": "DAOVote.vote_accounts" + }, + { + "name": "token", + "type": "FungibleTokenFull" + }, + { + "name": "author", + "type": "address" + } + ] + }, + "typedefs": [ + { + "name": "vote_option", + "typedef": "bool", + "vars": [] + }, + { + "name": "amount", + "typedef": "int", + "vars": [] + }, + { + "name": "vote_state", + "typedef": { + "map": ["DAOVote.vote_option", "DAOVote.amount"] + }, + "vars": [] + }, + { + "name": "vote_accounts", + "typedef": { + "map": [ + "address", + { + "tuple": ["DAOVote.amount", "DAOVote.vote_option", "bool"] + } + ] + }, + "vars": [] + }, + { + "name": "metadata", + "typedef": { + "record": [ + { + "name": "subject", + "type": "VoteSubjects.subject" + }, + { + "name": "description", + "type": "string" + }, + { + "name": "link", + "type": "string" + } + ] + }, + "vars": [] + } + ] + } + } +] diff --git a/examples/bcl-indexer/abis/TokenSale.aci.json b/examples/bcl-indexer/abis/TokenSale.aci.json new file mode 100644 index 0000000..248d31c --- /dev/null +++ b/examples/bcl-indexer/abis/TokenSale.aci.json @@ -0,0 +1,503 @@ +[ + { + "namespace": { + "name": "ListInternal", + "typedefs": [] + } + }, + { + "namespace": { + "name": "List", + "typedefs": [] + } + }, + { + "namespace": { + "name": "String", + "typedefs": [] + } + }, + { + "contract": { + "event": { + "variant": [ + { + "Transfer": ["address", "address", "int"] + }, + { + "Allowance": ["address", "address", "int"] + }, + { + "Burn": ["address", "int"] + }, + { + "Mint": ["address", "int"] + }, + { + "Swap": ["address", "int"] + } + ] + }, + "functions": [ + { + "arguments": [], + "name": "aex9_extensions", + "payable": false, + "returns": { + "list": ["string"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "name", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "initial_owner_balance", + "type": { + "option": ["int"] + } + } + ], + "name": "init", + "payable": false, + "returns": "FungibleTokenFull.state", + "stateful": false + }, + { + "arguments": [], + "name": "meta_info", + "payable": false, + "returns": "FungibleTokenFull.meta_info", + "stateful": false + }, + { + "arguments": [], + "name": "total_supply", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [], + "name": "balances", + "payable": false, + "returns": "FungibleTokenFull.balances", + "stateful": false + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "balance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "swapped", + "payable": false, + "returns": { + "map": ["address", "int"] + }, + "stateful": false + }, + { + "arguments": [], + "name": "allowances", + "payable": false, + "returns": "FungibleTokenFull.allowances", + "stateful": false + }, + { + "arguments": [ + { + "name": "allowance_accounts", + "type": "FungibleTokenFull.allowance_accounts" + } + ], + "name": "allowance", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + } + ], + "name": "allowance_for_caller", + "payable": false, + "returns": { + "option": ["int"] + }, + "stateful": false + }, + { + "arguments": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "create_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + }, + { + "name": "value_change", + "type": "int" + } + ], + "name": "change_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "for_account", + "type": "address" + } + ], + "name": "reset_allowance", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "to_account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "transfer", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "value", + "type": "int" + } + ], + "name": "burn", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + }, + { + "name": "value", + "type": "int" + } + ], + "name": "mint", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [], + "name": "swap", + "payable": false, + "returns": { + "tuple": [] + }, + "stateful": true + }, + { + "arguments": [ + { + "name": "account", + "type": "address" + } + ], + "name": "check_swap", + "payable": false, + "returns": "int", + "stateful": true + } + ], + "kind": "contract_child", + "name": "FungibleTokenFull", + "payable": false, + "state": { + "record": [ + { + "name": "owner", + "type": "address" + }, + { + "name": "total_supply", + "type": "int" + }, + { + "name": "balances", + "type": "FungibleTokenFull.balances" + }, + { + "name": "meta_info", + "type": "FungibleTokenFull.meta_info" + }, + { + "name": "allowances", + "type": "FungibleTokenFull.allowances" + }, + { + "name": "swapped", + "type": { + "map": ["address", "int"] + } + } + ] + }, + "typedefs": [ + { + "name": "meta_info", + "typedef": { + "record": [ + { + "name": "name", + "type": "string" + }, + { + "name": "symbol", + "type": "string" + }, + { + "name": "decimals", + "type": "int" + } + ] + }, + "vars": [] + }, + { + "name": "allowance_accounts", + "typedef": { + "record": [ + { + "name": "from_account", + "type": "address" + }, + { + "name": "for_account", + "type": "address" + } + ] + }, + "vars": [] + }, + { + "name": "balances", + "typedef": { + "map": ["address", "int"] + }, + "vars": [] + }, + { + "name": "allowances", + "typedef": { + "map": ["FungibleTokenFull.allowance_accounts", "int"] + }, + "vars": [] + } + ] + } + }, + { + "contract": { + "functions": [ + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "price", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [], + "name": "token_contract", + "payable": false, + "returns": "FungibleTokenFull", + "stateful": false + }, + { + "arguments": [], + "name": "sale_type", + "payable": false, + "returns": "string", + "stateful": false + }, + { + "arguments": [], + "name": "version", + "payable": false, + "returns": "int", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + } + ], + "name": "buy", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "_1", + "type": "int" + }, + { + "name": "_2", + "type": "address" + } + ], + "name": "buy_with_affiliation", + "payable": true, + "returns": "unit", + "stateful": true + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + } + ], + "name": "set_beneficiary", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [], + "name": "beneficiary", + "payable": false, + "returns": "address", + "stateful": false + }, + { + "arguments": [ + { + "name": "_1", + "type": "address" + } + ], + "name": "set_owner", + "payable": false, + "returns": "unit", + "stateful": true + }, + { + "arguments": [], + "name": "owner", + "payable": false, + "returns": "address", + "stateful": false + } + ], + "kind": "contract_main", + "name": "TokenSale", + "payable": false, + "typedefs": [] + } + } +] diff --git a/examples/bcl-indexer/abis/bytecode_hashes.json b/examples/bcl-indexer/abis/bytecode_hashes.json new file mode 100644 index 0000000..01b9cfb --- /dev/null +++ b/examples/bcl-indexer/abis/bytecode_hashes.json @@ -0,0 +1,32 @@ +{ + "8.0.0": { + "AffiliationTreasury.aes": { + "hash": "63b2eb5c3b52b5580b271cf636e723f58129cc19cd8aaf22d187ecd198c352be", + "bytecode": "cb_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EWNRdG0iAAcMDAwBBAwBAAIDEdDDbLguFAYARPwjAAQCBAABA6+CAAIAP7kDfS8iERoL78CtLkFmZmlsaWF0aW9uVHJlYXN1cnkudXBkYXRlX3VuaXF1ZV9pbnZpdGVlcxEbxaCtQWludml0YXRpb25fY29kZXMRKjW9l5EuQWZmaWxpYXRpb25UcmVhc3VyeS51cGRhdGVfaW52aXRlcnMRLkSmwUFhZmZpbGlhdGlvbl90cmVlETa9jwMhLlNldC5uZXcRN+APpzEuTGlzdC5sZW5ndGgRO/jsnF1yZWNvcmRfc2FsZV90cmFuc2FjdGlvbhE8WfOzdWdldF9hZmZpbGlhdGlvbl9mZWVfcHJlY2lzaW9uET0eiWglZ2V0X3N0YXRlEUEPzJ0hd2l0aGRyYXcRRNZEHxFpbml0EUl4msQ1Lkxpc3QubGVuZ3RoXxFYwQBDSWdldF91bmlxdWVfaW52aXRlZRFbH3AsSWdldF9kaXJlY3RfaW52aXRlchFjUXRtJS5TZXQuc2l6ZRFlpeAPLUNoYWluLmV2ZW50EWd+q8d9Z2V0X2FmZmlsaWF0aW9uX2ZlZV9wZXJjZW50YWdlcxFvPAHaUWdldF9hZmZpbGlhdGlvbl90cmVlEXZl9aY5cGF5b3V0X3BlcmlvZHMRee/VSE1nZXRfaW52aXRhdGlvbl9jb2RlEXruE+tdZ2V0X2FjY3VtdWxhdGVkX3Jld2FyZHMRf+Ib9k1yZWdpc3Rlcl9pbnZpdGF0aW9uEYQLv7M9dW5pcXVlX2ludml0ZWVzEaXb68mtLkFmZmlsaWF0aW9uVHJlYXN1cnkudXBkYXRlX2ludml0ZXJfYmFsYW5jZRGq5C0CpS5yZWdpc3Rlcl9pbnZpdGF0aW9uX2NvZGUuJWxhbWJkYS44Ny42MS4wEbRdthZhcmVnaXN0ZXJfaW52aXRhdGlvbl9jb2RlEcAyh755Z2V0X2FmZmlsaWF0aW9uX2ZlZV9wZXJjZW50YWdlEcPyLzw1Lkxpc3QuZm9yZWFjaBHQw2y4LS5TZXQuaW5zZXJ0EdG3ZtQtLlNldC5tZW1iZXIR1NiEY1lyZWRlZW1faW52aXRhdGlvbl9jb2RlEdosIKRZcmV2b2tlX2ludml0YXRpb25fY29kZRHhnwmqRWdldF9wYXlvdXRfcGVyaW9kEeHwajidLkFmZmlsaWF0aW9uVHJlYXN1cnkubmV3X2ludml0ZWVzX3N0YXRlgi8AhTguMC4wARoWh5k=" + }, + "DAO.aes": { + "hash": "1a9e086ef8cdf57ce6ef20cd683581bfa25b5cc7133784b96d9ae00fb28b165a", + "bytecode": "cb_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ZW4RiThL3EFmaW5hbF92b3RlX3N0YXRlEYnUrTctcmV2b2tlX3ZvdGURj24v2kljdXJyZW50X3ZvdGVfc3RhdGURqsDChjkuU3RyaW5nLmxlbmd0aBGwPjGwJWhhc192b3RlZBHJ9p+dMWNsb3NlX2hlaWdodBHsbUHhHXZlcnNpb24R8Op4nSVpc19jbG9zZWSCLwCFOC4wLjAAowAPAg4aChCEMQoSEAwCDgwCEkT8IwQEAAQCAxFlpeAPDwJvgibPDAN/DAIOJwwELSqEhBIMAhIMAg4nDAQA+wOFTk9fQ09NTVVOSVRZX01BTkFHRU1FTlRfQVZBSUxBQkxF/uHz1KYCNwGHAjcANwHnABcIPQACBAED/wEDf/7sbUHhADcABwEDAv7vy1DvAjcC5wCHAjcANwHnAOcADAECDAMrEReaei0/DAEABAMRJD/bEbkCXy8ZEQh+v+95LkRBTy5jYWxsX2NvbW11bml0eV9tYW5hZ2VtZW50ERTWCPIlZ2V0X3Rva2VuERTyIJORLmFwcGx5X3ZvdGVfc3ViamVjdC4lbGFtYmRhLjEzNy42Mi4zEReaei19Lk9wdGlvbi5kZWZhdWx0LiVsYW1iZGEuMTkuNjguMBEdsuaGkS5hcHBseV92b3RlX3N1YmplY3QuJWxhbWJkYS4xNDYuNjIuMBEkP9sRNS5PcHRpb24ubWF0Y2gRKTf63jlzZXRfdG9rZW5fc2FsZREtcF64kS5hcHBseV92b3RlX3N1YmplY3QuJWxhbWJkYS4xMzQuNjQuNBE567OykS5hcHBseV92b3RlX3N1YmplY3QuJWxhbWJkYS4xNDAuNjIuMhE7+OycXXJlY29yZF9zYWxlX3RyYW5zYWN0aW9uET0eiWglZ2V0X3N0YXRlEUNBSfeRLmFwcGx5X3ZvdGVfc3ViamVjdC4lbGFtYmRhLjE0My42Mi4xEUTWRB8RaW5pdBFGdRFJSWFwcGx5X3ZvdGVfc3ViamVjdBFRS7tdGWlzX2RhbxFb2WbxFXZvdGVzEWWl4A8tQ2hhaW4uZXZlbnQRbHc7nWFnZXRfY29tbXVuaXR5X21hbmFnZW1lbnQRcGesIB1mYWN0b3J5EZSyPds5Z2V0X3Rva2VuX3NhbGURldJ1OjF2b3RlX3RpbWVvdXQRtOe/3iFhZGRfdm90ZRHh89SmPS5PcHRpb24uaXNfbm9uZRHsbUHhHXZlcnNpb24R78tQ7z0uT3B0aW9uLmRlZmF1bHSCLwCFOC4wLjABE6DjKw==" + }, + "CommunityFactory.aes": { + "hash": "d7b06dacd86ba5834ef5ffa61a10aaf997e6ea43c23511e1853a9e17e304b08b", + "bytecode": "cb_+VwNRgOg69Asv9y6BSB1BOgG8W3vML9wpkRVfBcYggWk8rtTKPjAuVvfuViK/gSp5jgANwJ3d0cCDAEAAgMRy6Z1NQ8CAAwDACgsBAArEAIDAPwRBKnmODcARwIA/hNcCgQANwAHDAMADAKIAwD8EcAyh743AAcA/iaAcowCNwInhwI3AQc3AgcHBxczBAAHDBY1BgAANgYCAAg+AAQKRjoEAAAgJAIEBwwIGgkAAgYDAAED/0Y6BAAARjoGAAIiJAIEBwwUDAN/BgMOBwwSGgkAAgYDAAED/yEkAgYGAw4BA3/+KOgxlAA3AXdnd0cCDAEAAgMRy6Z1NQ8CACgsBAAA/jMyR4AENwN3ByeHAjcBBzcCBwd3GgoAgi8YAAAmAAcMBPsDZWNvbGxlY3Rpb25fQUxSRUFEWV9FWElTVFMZPBQkFgxvggHrCwAgAAcMCPsDlUNPTExFQ1RJT05fQ1JFQVRJT05fRE9OQVRJT05fTUlTTUFUQ0hVADwADAMFLQwBAAIDEauIMtECAxGriDLRDwIKDAEEDAECDAMvACcMBi0qgoIKCwBlA58AoAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADAIKVQBE/CMIBAIEAgMRZaXgDw8Cb4ImzwECCv42vY8DAjcAZ+cANwABAy8A/jnisEUANwF3BwwBAAIDEcumdTUPAgAoLAIAAP49HoloADcANwZndzcDJ4cCNwEHNwIHBwdnd0cCZ0cANwBnRwJHAkcCRwJHAgwCggwChAwChgwCiAwCigwCjCcMDAD+RNZEHwA3AXc3AAIDETa9jwMPAgIMAwAMAzcADAOPb4IOAfkOPkYDoCWnEVngr6yq3ZBjbAD2BEsUM0auEC4feBEaoiVNdP6DwLkOELkKiv4aC+/AAjcCRwAHNwAMAQACAxFbH3AsDwIACD4ABAYBAz9GOgIAAAIDETa9jwMMAy8ARPwjAAQCBCwqBogCCD4GCgwBAz9GOggGAEY6CgYCDAIIDAEAAgMR0bdm1AcMFAwCCgwCCAwBAgwBAAIDEeHwajgtKoiIAgEDPwEDP/4bxaCtADcAZ0cANwNHAAcXAQKG/io1vZcCNwRHAEcABycHNwAzBAYHDAw1BgAGNgYCBgwBAAIDEVsfcCwPAgQIPgQGCAEDP0Y6BgQAGTwUChYMAhYkBAAXAAwCBgIDEaXb68kPAm+CJs8aCQAGGgkGAgYDAAEDP/4uRKbBADcAZ0cARwABAoT+Nr2PAwI3AGfnADcAAQMvAP434A+nAjcBJ+cABwwDAAwBAAQDEUl4msT+O/jsnAQ3AkcABzcAGTwUChYMAgwBAgIDEcAyh74WABcCAAsAIiAABwwG+wPFQU1PVU5UX0lTX05PVF9FUVVBTF9UT19USEVfQUZGSUxJQVRJT05fUEVSQ0VOVEFHRQwDQ2+B7G89ZDIMAQIMAQAMAQACAxEqNb2XDwJvgibPDAECDAEAAgMRGgvvwA8Cb4ImzwwBAAwBAkT8cwQEBAYGBAQMBAQDEWWl4A/+PFnzswA3AAcZPBQKFgwCAP49HoloADcANwRnB2dHAAdnRwBHAGdHADcDRwAHF2dHAIcCNwA3AmdHADcAZ0cABwwCggwChAwChgwCiCcMCAD+QQ/MnQA3ADcAGgoAiAwDr4IAAgA/AgMRNr2PAwwDLwBE/CMABAIEVQAsCAAgAAcMBvsDmU1JTklNVU1fQUNDT1VOVFNfVEhSRVNIT0xEX05PVF9SRUFDSEVEVQACAxF67hPrDwIGVQBlCAYCAxHhnwmqDwISLOoUghIvAFUALcgUAC0qgoISDAMCAgMR4Z8JqhUCKCzqKoIoLwBVAC3IKgAtKoKCKFUADAIGRPxzBAQEBgYEBAQEBAMRZaXgD/5E1kQfADcANwAaDoIvABoOhC8AGg6GLwAaDogvAAEDP/5JeJrEAjcCJ+cABwczBAAHDAQ2BQAAEQECBgMAAQEC/ljBAEMANwFHAIcCNwA3AmdHADcAZ0cABysYiAAA/lsfcCwANwFHAIcCNwA3AUcAGgoAhC8YhAAHDAQBA6+CAAEAPysYAABE/CMAAgICAP5jUXRtAjcBZ+cANwAHMQQAAP5lpeAPAjcBhwc3AkcARwA3AkcABzcCRwAHNwNHAEcABzcDRwBHAEcANwJHAEcANwJHAAc3AAoNAHMCBAYICgwORjYAAABGNgIAAmOvX58BgfbUhTczWmBZSbUsFiE/p4q80hYW36iKv19++D59z7NZAAIBAz9GNgAAAEY2AgACY69fnwGBWXt22wRHiJN+OIPVVdGx2fL04jvHEVOlQECaqUWZfm8AAgEDP0Y2AAAARjYCAAJjr1+fAYG/e7dyQcQFTgd8uZ9ojnFUgzTOF6npCcZrCuxL2Tv6RwACAQM/RjYAAABGNgIAAkY2BAAEZAKvX58BgURKmoQvk3ac1MVJnkwWPk0BapZSvRD9xdWi/6yamj04AAIEAQM/RjYAAABGNgIAAkY2BAAEZAKvX58BgRdp9PvzrJcr65iTEH48ldu8LKfeS7WSikbP2uf99hppAAIEAQM/RjYAAABGNgIAAmOvX58BgWKTtSJXlUgqBvWRPGDWscA0er6HHTJ1rUebCXWXbiXIAAIBAz9GNgAAAEY2AgACY69fnwGBqn8eXjRxUAyZicrk69/xWN5suZs3lRXMdo5isIeUxvAAAgEDP/5nfqvHADcAJwcBA0NvgexvPWQy/m88AdoANwFHAEcAKxiEAAD+dmX1pgA3AGcHZ0cABwECgv5579VIADcBRwA3A0cABxcrGIYAAP567hPrADcBRwAHGgoAghoKAoIMAwAMAQAMAy8ADAMCAgMR4Z8JqhUALAgCLAAMAwAMAQAMAy8AAgMR4Z8JqiwIACwAFAAA/n/iG/YANwFHADcAGgoAhFUALwgAJgAHDAT7A2lJTlZJVEVFX0FMUkVBRFlfUkVHSVNURVJFRFUALUqEhABVAAwBAET8cwQEBAYGBAQABAQDEWWl4A/+hAu/swA3AGdHAIcCNwA3AmdHADcAZ0cABwECiP6l2+vJAjcCRwAHNwACAxHhnwmqDwIILOoKgggvACzaDAoAABQYDAItGAoALSqCgggMAQAMAQJE/HMEBAQGBgQEAgQEAxFlpeAP/qrkLQICNwL39/coHgAAACgeAgIAZQkCAhoKBoYvGAYCJgAHDAT7A3VJTlZJVEFUSU9OX0FMUkVBRFlfUkVHSVNURVJFRFUADAIADAN/JwwGLRqGhgJVAAwBAgwCAET8cwQEBAYGBAQGBgQDEWWl4A/+tF22FgQ3AydHAAcHNwAZPgAUHiIkAgAHDAT7A41NSU5JTVVNX1JFREVNUFRJT05fQU5EX0ZFRV9OT1RfTUVFVAwBAAIDETfgD6cUFAIEFgALACAABwwK+wOZSU5WSVRBVElPTl9BTU9VTlRfQU5EX0ZFRV9OT1RfTUFUQ0hJTkcMAxGq5C0CDAEEDAECJwwEJwwEDAEABAMRw/IvPP7AMoe+ADcABwEDb4IBtP7D8i88AjcCJ+cANwJ39zcAMwQABwwGNQQAKBwCAigcAAICAA8Cb4ImzzYFAAAGAwABAz/+0MNsuAI3AucAZ+cANwBn5wA3AC3UAgA/AP7Rt2bUAjcC5wBn5wA3ABcvFAIAAP7U2IRjADcBRwA3AFUCABoKAoYvKIYABwwWDAOvggABAD8PAgYIPgYUBEY6CAYAKC4KAAgoLgwCCCguDgQIJggOBwwI+wNBQUxSRUFEWV9SRURFRU1FRCMYCgAHDAz7A1VJTlZJVEVSX0VRVUFMX0lOVklURUUMAgoMAgwMA/8nDAZVAC0KhoYMAQAMAgpVAET8cwQEBAYGBAQIBgIDEWWl4A8PAm+CJs9lCQAMGgouhC8YLgAmAAcMEvsDaUlOVklURUVfQUxSRUFEWV9SRUdJU1RFUkVELZqEhAAKAQM/+wNlSU5WSVRBVElPTl9OT1RfUkVHSVNURVJFRCsoAgBE/CMAAgICDwIGCD4GFAT+2iwgpAA3AUcANwAaCgCGLxiGAAcMEgwDr4IAAQA/DwIECD4EEARGOgYEACguCAAGKC4KAgYoLgwEBiYIDAcMCPsDQUFMUkVBRFlfUkVERUVNRURVACAgCAcMDPsDSUNBTExFUl9OT1RfSU5WSVRFUlUAZQgKDAEADAIIRPxzBAQEBgYEBAoEAgMRZaXgDw8Cb4Imzy4ahoYAAQM/+wNlSU5WSVRBVElPTl9OT1RfUkVHSVNURVJFRCsYAABE/CMAAgICDwIECD4EEAT+4Z8JqgA3AAdYABcwb4SafsfAAP7h8Go4AjcERwAHZ0cANwBnRwAHhwI3ADcCZ0cANwBnRwAHLNQGAAAUEgACGTwUJBYMFCIIAAcMBAwBBC2UBgAARPwjAAQCBAAMAwYMAQQCAxFjUXRtIgAHDAwMAQQMAQACAxHQw2y4LhQGAET8IwAEAgQAAQOvggACAD+5A30vIhEaC+/ArS5BZmZpbGlhdGlvblRyZWFzdXJ5LnVwZGF0ZV91bmlxdWVfaW52aXRlZXMRG8WgrUFpbnZpdGF0aW9uX2NvZGVzESo1vZeRLkFmZmlsaWF0aW9uVHJlYXN1cnkudXBkYXRlX2ludml0ZXJzES5EpsFBYWZmaWxpYXRpb25fdHJlZRE2vY8DIS5TZXQubmV3ETfgD6cxLkxpc3QubGVuZ3RoETv47JxdcmVjb3JkX3NhbGVfdHJhbnNhY3Rpb24RPFnzs3VnZXRfYWZmaWxpYXRpb25fZmVlX3ByZWNpc2lvbhE9HoloJWdldF9zdGF0ZRFBD8ydIXdpdGhkcmF3EUTWRB8RaW5pdBFJeJrENS5MaXN0Lmxlbmd0aF8RWMEAQ0lnZXRfdW5pcXVlX2ludml0ZWURWx9wLElnZXRfZGlyZWN0X2ludml0ZXIRY1F0bSUuU2V0LnNpemURZaXgDy1DaGFpbi5ldmVudBFnfqvHfWdldF9hZmZpbGlhdGlvbl9mZWVfcGVyY2VudGFnZXMRbzwB2lFnZXRfYWZmaWxpYXRpb25fdHJlZRF2ZfWmOXBheW91dF9wZXJpb2RzEXnv1UhNZ2V0X2ludml0YXRpb25fY29kZRF67hPrXWdldF9hY2N1bXVsYXRlZF9yZXdhcmRzEX/iG/ZNcmVnaXN0ZXJfaW52aXRhdGlvbhGEC7+zPXVuaXF1ZV9pbnZpdGVlcxGl2+vJrS5BZmZpbGlhdGlvblRyZWFzdXJ5LnVwZGF0ZV9pbnZpdGVyX2JhbGFuY2URquQtAqUucmVnaXN0ZXJfaW52aXRhdGlvbl9jb2RlLiVsYW1iZGEuODcuNjEuMBG0XbYWYXJlZ2lzdGVyX2ludml0YXRpb25fY29kZRHAMoe+eWdldF9hZmZpbGlhdGlvbl9mZWVfcGVyY2VudGFnZRHD8i88NS5MaXN0LmZvcmVhY2gR0MNsuC0uU2V0Lmluc2VydBHRt2bULS5TZXQubWVtYmVyEdTYhGNZcmVkZWVtX2ludml0YXRpb25fY29kZRHaLCCkWXJldm9rZV9pbnZpdGF0aW9uX2NvZGUR4Z8JqkVnZXRfcGF5b3V0X3BlcmlvZBHh8Go4nS5BZmZpbGlhdGlvblRyZWFzdXJ5Lm5ld19pbnZpdGVlc19zdGF0ZYIvAIU4LjAuMAGjAA8CBgwDAAwDNwAMA49vggh/+Qi8RgOgpogXQAoIKEhpxbTkB2/oSjyRXuuzg1600Ttf0XylZubAuQiOuQYz/igET3IANwAHAQNvgiae/i1z7aEANwAHGTwUFhYMAgD+LYNHBwA3AAcZPBQYFgwCAP4udHW5ADcABxk8FBQWDAIA/jWhqu0CNwGHAzcCBwc3ADcCBwcHCf0AAgQGRjQAAgABAwJGNAACAP5ELIR9ADcCBwcHDAECFRQAAgIDEYev/i0PAgAWOABvgiaeFzBvgibQAP5E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EXZvdGURNXVFHR1zdWJqZWN0ET0eiWglZ2V0X3N0YXRlEUEPzJ0hd2l0aGRyYXcRRNZEHxFpbml0EU2cGB8xdm90ZWRfb3B0aW9uEWOU6XohbWV0YWRhdGERZM4vszV2b3RlX2FjY291bnRzEWWl4A8tQ2hhaW4uZXZlbnQRalum2TVoYXNfd2l0aGRyYXduEXs+/AoVdG9rZW4RiThL3EFmaW5hbF92b3RlX3N0YXRlEYnUrTctcmV2b2tlX3ZvdGURj24v2kljdXJyZW50X3ZvdGVfc3RhdGURqsDChjkuU3RyaW5nLmxlbmd0aBGwPjGwJWhhc192b3RlZBHJ9p+dMWNsb3NlX2hlaWdodBHsbUHhHXZlcnNpb24R8Op4nSVpc19jbG9zZWSCLwCFOC4wLjAAowAPAg4aChCEMQoSEAwCDgwCEkT8IwQEAAQCAxFlpeAPDwJvgibPDAN/DAIOJwwELSqEhBIMAhIMAg4nDAQA+wOFTk9fQ09NTVVOSVRZX01BTkFHRU1FTlRfQVZBSUxBQkxF/uHz1KYCNwGHAjcANwHnABcIPQACBAED/wEDf/7sbUHhADcABwEDAv7vy1DvAjcC5wCHAjcANwHnAOcADAECDAMrEReaei0/DAEABAMRJD/bEbkCXy8ZEQh+v+95LkRBTy5jYWxsX2NvbW11bml0eV9tYW5hZ2VtZW50ERTWCPIlZ2V0X3Rva2VuERTyIJORLmFwcGx5X3ZvdGVfc3ViamVjdC4lbGFtYmRhLjEzNy42Mi4zEReaei19Lk9wdGlvbi5kZWZhdWx0LiVsYW1iZGEuMTkuNjguMBEdsuaGkS5hcHBseV92b3RlX3N1YmplY3QuJWxhbWJkYS4xNDYuNjIuMBEkP9sRNS5PcHRpb24ubWF0Y2gRKTf63jlzZXRfdG9rZW5fc2FsZREtcF64kS5hcHBseV92b3RlX3N1YmplY3QuJWxhbWJkYS4xMzQuNjQuNBE567OykS5hcHBseV92b3RlX3N1YmplY3QuJWxhbWJkYS4xNDAuNjIuMhE7+OycXXJlY29yZF9zYWxlX3RyYW5zYWN0aW9uET0eiWglZ2V0X3N0YXRlEUNBSfeRLmFwcGx5X3ZvdGVfc3ViamVjdC4lbGFtYmRhLjE0My42Mi4xEUTWRB8RaW5pdBFGdRFJSWFwcGx5X3Zv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Js8tao6OBAJVAAwBAAwBAkT8UwYGBAQEAgYEAxFlpeAP/v6upPoANwBHAAECgrkCpi8dEQMUe82xLkZ1bmdpYmxlVG9rZW5GdWxsLmludGVybmFsX2NoYW5nZV9hbGxvd2FuY2UREQBPphFzd2FwERQ3tDglbWV0YV9pbmZvER3sZv8dc3dhcHBlZBEh3/q2SXRyYW5zZmVyX2FsbG93YW5jZREjw1xqPXJlc2V0X2FsbG93YW5jZREtnTTekS5GdW5naWJsZVRva2VuRnVsbC5yZXF1aXJlX2FsbG93YW5jZRExwI1zPWFleDlfZXh0ZW5zaW9ucxE9hVqOQWNoYW5nZV9hbGxvd2FuY2URPmx4M1FhbGxvd2FuY2VfZm9yX2NhbGxlchFE1kQfEWluaXQRZaXgDy1DaGFpbi5ldmVudBFqABZeJWFsbG93YW5jZRF2S4FBiS5GdW5naWJsZVRva2VuRnVsbC5yZXF1aXJlX2JhbGFuY2URgCRrRyFiYWxhbmNlcxGEoV2hIXRyYW5zZmVyEYvH9MbFLkZ1bmdpYmxlVG9rZW5GdWxsLnJlcXVpcmVfYWxsb3dhbmNlX25vdF9leGlzdGVudBGXBXnMtS5GdW5naWJsZVRva2VuRnVsbC5yZXF1aXJlX25vbl9uZWdhdGl2ZV92YWx1ZRGqwMKGOS5TdHJpbmcubGVuZ3RoEbHvwXsRYnVybhG0jBaEHWJhbGFuY2URwnAhIoEuRnVuZ2libGVUb2tlbkZ1bGwucmVxdWlyZV9vd25lchHP3ZqiEW1pbnQR1jkNfiljaGVja19zd2FwEddMFd4pYWxsb3dhbmNlcxHbY3WoMXRvdGFsX3N1cHBseRHtkXzfkS5GdW5naWJsZVRva2VuRnVsbC5pbnRlcm5hbF90cmFuc2ZlchHvzFjhQWNyZWF0ZV9hbGxvd2FuY2UR/q6k+hVvd25lcoIvAIU4LjAuMACjAA8CBgwBClUAAgMR78tQ7w8CCFUAgAKKGgqCBhoGhAgaBoYMGgqICBoGjAAaCo4AAQM//kVtSH0ANwEHBx80AAAHDAT7A0lDT1VOVF9OT1RfUE9TSVRJVkUMAQAMAwAMAoIDAPwR22N1qDcABwwDAAwChAMA/BFELIR9NwIHBwcA/mWl4A8CNwGHAzcDBwcHNwIHBzcCBwc3AAn9AAIEBkY2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j7hIADcARwIBAor+0bHJjgI3AXcnB5wEAAD+0bdm1AI3AucAZ+cANwAXLxQCAAD+1rBTvgA3AgdHADcADAKEVQACAxHRt2bUBwwG+wNRTk9UX0tOT1dOX1RPS0VOX1NBTEUWNABvggOoDAECDAMADAKMAwD8Ec/dmqI3AkcABzcAAP7bQWJZADcBdyeHAjcBBzcCBwcMAQACAxHLpnU1DwIAKCwAAAD+7G1B4QA3AAcBAwL++FrUmgA3And3FwwBAAIDEcumdTUPAgAoLAQALxACALkDTC8iEQSp5jg5dG9rZW5fY29udHJhY3QRE1wKBDlmZWVfcGVyY2VudGFnZREmgHKMkS5Db21tdW5pdHlGYWN0b3J5LmFsbG93ZWRfY2hhcl9yYW5nZREo6DGUTXRva2VuX3NhbGVfcmVnaXN0cnkRMzJHgEVjcmVhdGVfY29sbGVjdGlvbhE2vY8DIS5TZXQubmV3ETnisEVNYWxsb3dlZF9uYW1lX2xlbmd0aBE9HoloJWdldF9zdGF0ZRFE1kQfEWluaXQRTLcd3FFhZmZpbGlhdGlvbl90cmVhc3VyeRFNks9erS5Db21tdW5pdHlGYWN0b3J5LnJlcXVpcmVfbmFtZV9yZXN0cmljdGlvbnMRWuaWM1Fjb21tdW5pdHlfbWFuYWdlbWVudBFhcvmGlS5Db21tdW5pdHlGYWN0b3J5LnJlcXVpcmVfbmFtZV91bmlxdWURYc1Q4SUuTGlzdC5hbGwRZaXgDy1DaGFpbi5ldmVudBFsdzudYWdldF9jb21tdW5pdHlfbWFuYWdlbWVudBF3zGOYQWNyZWF0ZV9jb21tdW5pdHkRjsHTljVmZWVfcHJlY2lzaW9uEZSyPds5Z2V0X3Rva2VuX3NhbGURlyhCsUlwcm90b2NvbF9kYW9fdG9rZW4RobL9s/EuQ29tbXVuaXR5RmFjdG9yeS5yZXF1aXJlX25hbWVfcmVzdHJpY3Rpb25zLiVsYW1iZGEuMTYyLjM4LjARqsDChjkuU3RyaW5nLmxlbmd0aBGriDLROS5TdHJpbmcuY29uY2F0Ea7zptlpLkNvbW11bml0eUZhY3RvcnkuZGVjaW1hbHMRtRfsKjFmYWN0b3J5X3R5cGURy6Z1NZEuQ29tbXVuaXR5RmFjdG9yeS5yZXF1aXJlX2NvbGxlY3Rpb24R0MNsuC0uU2V0Lmluc2VydBHRj7hINWJvbmRpbmdfY3VydmUR0bHJjj0uU3RyaW5nLnRvX2xpc3QR0bdm1C0uU2V0Lm1lbWJlchHWsFO+XW1pbnRfcHJvdG9jb2xfZGFvX3Rva2VuEdtBYllJYWxsb3dlZF9uYW1lX2NoYXJzEextQeEddmVyc2lvbhH4WtSaNWhhc19jb21tdW5pdHmCLwCFOC4wLjAAllwrcw==" + }, + "CommunityManagement.aes": { + "hash": "f90e69fb8693adc7955586a2ae77c5f02b566861e6d8706279dd0af9017d01a6", + "bytecode": "cb_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" + }, + "DAOVote.aes": { + "hash": "235f88c81ec84f5a6bee4ff9e221bee6b687b1cb65f0086e0dad3caf4ad0d346", + "bytecode": "cb_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" + }, + "BondingCurveExponential.aes": { + "hash": "386522ce25ded384179fcaf7d1c7dff5d2e16464e0ce1d7519bfdc101cb5751b", + "bytecode": "cb_+Qi8RgOgVw8C4KG7ouMzoWA3gcsfe68sWTSe1ZC5BcvFY00TaZDAuQiOuQYz/igET3IANwAHAQNvgiae/i1z7aEANwAHGTwUFhYMAgD+LYNHBwA3AAcZPBQYFgwCAP4udHW5ADcABxk8FBQWDAIA/jWhqu0CNwGHAzcCBwc3ADcCBwcHCf0AAgQGRjQAAgABAwJGNAACAP5ELIR9ADcCBwcHDAECFRQAAgIDEYev/i0PAgAWOABvgiaeFzBvgibQAP5E1kQfADcANwAaDoI/AQM//k9TnfQANwB3AQNVVEFZTE9SX0VYUE9ORU5USUFMX1Yx/lNMfrICNwGHAzcCBwc3ADcCBwcHCf0AAgQGRjQAAAABAwBGNgAAABUsAAAA/lR9m8cCNwGHAzcCBwc3ADcCBwcHCf0AAgQGRjYAAABGNgIAAhQoAAISFyACAAEDAEY2AAAARjYCAAIXKAACFQwAAP5ajfaeADcBBwcMAQACAxGsrn7HBAMRelYXtP5ni637AjcBhwM3AgcHNwA3AgcHhwM3AgcHNwA3AgcHCf0AAgYIRjYAAABGNgIAAgwCAgwCAAIDEZ4LWLMPAgQXKAAEFygCBET8MwQABAAEAAEDr4MCAAIBP0Y2AAAARjYCAAIMAgIMAgACAxGeC1izDwIEFygABBcoAgRE/DMEAAQEBAD+bzKn5QI3AQcHGTwUJBYMAhk8FCQWDAIWAAwDBAwDAAwBAAwBAAQDEeX0N47+cg5TGgA3AQeHAzcCBwc3ADcCBwcZPBQkFgwCGTwUFBYMAhYQABcCABk8FCQWDAIMAwIZPBQkFgwCGTwUJBYMAgwCAAIDEeX0N44PAgIZPBQkFgwCGTwUJBYMAhYAGTwUJBYMAhUIAhk8FB4WDAIWAAIDEYJ/04MPAgQZPBQkFgwCGTwUFhYMAgIDEYJ/04MMAgQEAxGfYMjs/npWF7QCNwGHAzcCBwc3ADcCBwcHCf0AAgQGRjYAAABGNgIAAhcoAAIAAQMARjYAAABGNgIAAhQoAAISFyACFQwAAP6Cf9ODAjcCBweHAzcCBwc3ADcCBwcgNAIABwwWBgMEIDQAAAcMFB40AgAeNAAAIAAHDA4MAQACAxHf5pvPDAECAgMR3+abz0T8MwQABAQEBAMRZ4ut+wwBAAIDEd/mm88MAQICAxHf5pvPRPwzBAAEAAQEAxFni637AQOvgwIAAgE/+wNBWmVybyBkZW5vbWluYXRvcv6Hr/4tAjcCBwcHGTwUGBYMAiIEAgcMBPsDXU1JTklNVU1fVE9LRU5TX1JFUVVJUkVEFBYEAAIZPBQUFgwCFhIGABk8FBQWDAIWIggEGTwUJBYMAhk8FBQWDAIWAAwCBgIDEW8yp+UMAggCAxFvMqflFQAZPBQeFgwCFgAXABk8FCQWDAIZPBQWFgwCFhACFwAUAAD+jQLH6gA3AAcBA2+CJp7+kLYRZAI3AocDNwIHBzcANwIHB4cDNwIHBzcANwIHB4cDNwIHBzcANwIHBwwBAgIDETWhqu0MAQACAxE1oartFgAMAQICAxFTTH6yDAEAAgMRU0x+shYABAMRgn/Tg/6eC1izAjcCBwcHIDQCAAcMBAwBAhgVAgACDwEABgMAAQEA/p9gyOwCNwKHAzcCBwc3ADcCBweHAzcCBwc3ADcCBweHAzcCBwc3ADcCBwcMAQACAxHz3iApDwIAKC4CAAAoLgQCAAwBAgIDEfPeICkPAgYoLggABiguCgIGICgECgcMCBYoBAoWKAgEFigCChQABAMRgn/TgwwCBBQoAggEAxGCf9OD/qyufscANwEHhwM3AgcHNwA3AgcHDANvgibQDANvgiaeAgMRgn/TgwwBAAIDEXIOUxoEAxGQthFk/rQrD/UANwEHBwwBAAIDEXIOUxoEAxFUfZvH/tOTlJoANwAHAQMk/t5pwY0ANwIHBwcMAQIMAQAEAxGHr/4t/t/mm88CNwEHBx40AAAHDAQBAQAVHAAAAP7l9DeOAjcFBwcHBwcHHzQGbyQHDAoeNAICBgMEBwwIFhQGCBYUAgAXAgQaCQIEFCUEBAQRAQYGAwABAQQMA/8GAwT+894gKQI3AYcDNwIHBzcANwIHBzcCBwcJ/QACBAZGNAAARjQAAicMBAABAysAAkY2AAAAFSwAAEY0AAInDAQAuQJSLxwRKARPcmVnZXRfc2VsbF9yZXR1cm5fcHJlY2lzaW9uES1z7aFFZ2V0X2luaXRpYWxfcHJpY2URLYNHB0VnZXRfbWluaW11bV9jb3VudBEudHW5FWdldF9rETWhqu0lLkZyYWMuZGVuEUQshH1VY2FsY3VsYXRlX3NlbGxfcmV0dXJuEUTWRB8RaW5pdBFPU530KWN1cnZlX3R5cGURU0x+siUuRnJhYy5udW0RVH2bxykuRnJhYy5jZWlsEVqN9p4pc2VsbF9wcmljZRFni637OS5GcmFjLnNpbXBsaWZ5EW8yp+VxLkJvbmRpbmdDdXJ2ZUV4cG9uZW50aWFsLm1jMhFyDlMaJWJ1eV9jdXJ2ZRF6Vhe0LS5GcmFjLmZsb29yEYJ/04M9LkZyYWMubWFrZV9mcmFjEYev/i2hLkJvbmRpbmdDdXJ2ZUV4cG9uZW50aWFsLmNhbGN1bGF0ZV9wcmljZRGNAsfqaWdldF9zZWxsX3JldHVybl9wZXJjZW50YWdlEZC2EWQlLkZyYWMubXVsEZ4LWLMlLkZyYWMuZ2NkEZ9gyOwlLkZyYWMuYWRkEayufscpc2VsbF9jdXJ2ZRG0Kw/1JWJ1eV9wcmljZRHTk5SaSXN1cHBvcnRlZF9kZWNpbWFscxHeacGNTWNhbGN1bGF0ZV9idXlfcHJpY2UR3+abzzUuRnJhYy5hYnNfaW50EeX0N46NLkJvbmRpbmdDdXJ2ZUV4cG9uZW50aWFsLmV4cF9oZWxwZXIR894gKTUuRnJhYy50b19wYWlygi8AhTguMC4wAKnjHWo=" + }, + "AffiliationBondingCurveTokenSale.aes": { + "hash": "8aad83621943ee70f54561e29f4e60e4eefa2f110bf3cf2bc9a03804497a728a", + "bytecode": "cb_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VkUMAQAMAwAMAoIDAPwR22N1qDcABwwDAAwChAMA/BHeacGNNwIHBwcPAgQMAgQCAxHYjkruDwIGFCgEBgD+2I5K7gI3AQcHDAMADAKGAwD8EcAyh743AAcPAgAMAwAMAoYDAPwRPFnzszcABxYkAAAXAAD+7G1B4QA3AAcBAwL+78tQ7wI3AucAhwI3ADcB5wDnAAwBAgwDKxEXmnotPwwBAAQDESQ/2xH+/q6k+gA3AEcAAQKIuQJkLxgRBKnmODl0b2tlbl9jb250cmFjdBEL2dx+LWJlbmVmaWNpYXJ5ERXWKAENYnV5EReaei19Lk9wdGlvbi5kZWZhdWx0LiVsYW1iZGEuMTkuNjguMBEkP9sRNS5PcHRpb24ubWF0Y2gRNn+s1iVzZXRfb3duZXIRPR6JaCVnZXRfc3RhdGURP4mLZNkuQWZmaWxpYXRpb25Cb25kaW5nQ3VydmVUb2tlblNhbGUuY2FsY3VsYXRlX3VuaXRfcHJpY2URRNZEHxFpbml0EUVtSH0tc2VsbF9yZXR1cm4RZaXgDy1DaGFpbi5ldmVudBF//Wo/vS5BZmZpbGlhdGlvbkJvbmRpbmdDdXJ2ZVRva2VuU2FsZS5yZXF1aXJlX293bmVyEYkf0ygRc2VsbBGOsfY78S5BZmZpbGlhdGlvbkJvbmRpbmdDdXJ2ZVRva2VuU2FsZS5idXlfd2l0aF9hZmZpbGlhdGlvbl9pbm5lchG7tbDUUWJ1eV93aXRoX2FmZmlsaWF0aW9uEcFN9qg9c2V0X2JlbmVmaWNpYXJ5EcONeH6xLkFmZmlsaWF0aW9uQm9uZGluZ0N1cnZlVG9rZW5TYWxlLnZlcmlmeV9kYW8RyLRS+iVzYWxlX3R5cGUR0Y+4SDVib25kaW5nX2N1cnZlEdS9e8EVcHJpY2UR2I5K7tEuQWZmaWxpYXRpb25Cb25kaW5nQ3VydmVUb2tlblNhbGUuYWZmaWxpYXRpb25fYW1vdW50EextQeEddmVyc2lvbhHvy1DvPS5PcHRpb24uZGVmYXVsdBH+rqT6FW93bmVygi8AhTguMC4wAAigklM=" + } + } +} diff --git a/examples/bcl-indexer/abis/source_hashes.json b/examples/bcl-indexer/abis/source_hashes.json new file mode 100644 index 0000000..ba774d3 --- /dev/null +++ b/examples/bcl-indexer/abis/source_hashes.json @@ -0,0 +1,11 @@ +{ + "AffiliationTreasury.aes": "hRPOYcgyS3Q8u4NKO+SFqL80nMbd6hbD1Id6KowDDN4=", + "DAO.aes": "0C32YkPv/2WZjIhMuC2I+YX62VnZTBhGbPkhnnQeJm8=", + "CommunityFactory.aes": "69Asv9y6BSB1BOgG8W3vML9wpkRVfBcYggWk8rtTKPg=", + "CommunityManagement.aes": "CsxQG0PMThvFa98cMZgwmSTEkxRtkNFdLxW3ZIp4LNg=", + "DAOVote.aes": "EO9nqbmVzhMpEhSrXLu1vpauCv7FIVh/8NVfsL1xLPI=", + "BondingCurveExponential.aes": "Vw8C4KG7ouMzoWA3gcsfe68sWTSe1ZC5BcvFY00TaZA=", + "AffiliationBondingCurveTokenSale.aes": "/nFvNKkmjsTYwsMRBc8JVBTMBLrqJ7IDaUgiA8uewEU=", + "interfaces/TokenSale.aes": "8v6nzCGYPeHDDwsm65L3JNYl1UFR9gsdJnSiaSXhHao=", + "interfaces/BondingCurve.aes": "rIesN4WZvy9QaYG1AgX45oxS6DvjFV8r5Bnm/lsRNgk=" +} diff --git a/examples/bcl-indexer/aesync-env.d.ts b/examples/bcl-indexer/aesync-env.d.ts new file mode 100644 index 0000000..62a0b91 --- /dev/null +++ b/examples/bcl-indexer/aesync-env.d.ts @@ -0,0 +1,37 @@ +// Auto-generated by @growae/aesync — do not edit + +declare module 'aesync:registry' { + interface AeSyncRegistry { + fns: Array<{ name: string; fn: (...args: any[]) => Promise }> + _api_routes: Array<{ + method: string + path: string + handler: (...args: any[]) => any + }> + _api_middleware: Array<(...args: any[]) => any> + on( + name: + | 'ct_25cqTw85wkF5cbcozmHHUCuybnfH9WaRZXSgEcNNXG9LsCJWTN:CreateCommunity' + | 'ct_25cqTw85wkF5cbcozmHHUCuybnfH9WaRZXSgEcNNXG9LsCJWTN:CreateCollection' + | 'BclTokenSale:Buy' + | 'BclTokenSale:Sell' + | 'BclTokenSale:PriceChange', + fn: (...args: any[]) => Promise, + ): void + get(path: string, handler: (...args: any[]) => any): void + post(path: string, handler: (...args: any[]) => any): void + use(handler: (...args: any[]) => any): void + } + export const aesync: AeSyncRegistry +} + +declare module 'aesync:schema' { + export * from './schema.js' +} + +declare module 'aesync:api' { + export let db: any + export let client: any + export function setDb(d: any): void + export function setClient(c: any): void +} diff --git a/examples/bcl-indexer/aesync.config.ts b/examples/bcl-indexer/aesync.config.ts new file mode 100644 index 0000000..b3f4af7 --- /dev/null +++ b/examples/bcl-indexer/aesync.config.ts @@ -0,0 +1,36 @@ +import { createConfig } from '@growae/aesync' +import AffiliationBondingCurveTokenSaleAci from './abis/AffiliationBondingCurveTokenSale.aci.json' +import CommunityFactoryAci from './abis/CommunityFactory.aci.json' + +export default createConfig({ + network: { + name: 'mainnet', + mdwUrl: process.env.AE_MDW_URL ?? 'https://mainnet.aeternity.io/mdw', + mdwWsUrl: + process.env.AE_MDW_WS_URL ?? + 'wss://mainnet.aeternity.io/mdw/v3/websocket', + nodeUrl: 'https://mainnet.aeternity.io', + }, + database: { + kind: 'postgres', + connectionString: + process.env.DATABASE_URL ?? + 'postgresql://postgres:postgres@localhost:5432/bcl', + }, + contracts: { + BclFactory: { + aci: CommunityFactoryAci, + address: 'ct_25cqTw85wkF5cbcozmHHUCuybnfH9WaRZXSgEcNNXG9LsCJWTN', + startHeight: 1_089_546, + }, + BclTokenSale: { + aci: AffiliationBondingCurveTokenSaleAci, + factory: { + contract: 'BclFactory', + event: 'CreateCommunity', + parameter: 'arg2', + }, + }, + }, + port: 42069, +}) diff --git a/examples/bcl-indexer/docker-compose.yml b/examples/bcl-indexer/docker-compose.yml new file mode 100644 index 0000000..5b25354 --- /dev/null +++ b/examples/bcl-indexer/docker-compose.yml @@ -0,0 +1,19 @@ +services: + postgres: + image: postgres:16-alpine + environment: + POSTGRES_DB: bcl + POSTGRES_USER: postgres + POSTGRES_PASSWORD: postgres + ports: + - '5432:5432' + volumes: + - pgdata:/var/lib/postgresql/data + healthcheck: + test: ['CMD-SHELL', 'pg_isready -U postgres'] + interval: 5s + timeout: 5s + retries: 5 + +volumes: + pgdata: diff --git a/examples/bcl-indexer/package.json b/examples/bcl-indexer/package.json new file mode 100644 index 0000000..61879c3 --- /dev/null +++ b/examples/bcl-indexer/package.json @@ -0,0 +1,15 @@ +{ + "name": "bcl-indexer", + "version": "0.0.1", + "private": true, + "type": "module", + "scripts": { + "dev": "aesync dev", + "start": "aesync start", + "serve": "aesync serve", + "codegen": "aesync codegen" + }, + "dependencies": { + "@growae/aesync": "workspace:*" + } +} diff --git a/examples/bcl-indexer/schema.ts b/examples/bcl-indexer/schema.ts new file mode 100644 index 0000000..152ff7b --- /dev/null +++ b/examples/bcl-indexer/schema.ts @@ -0,0 +1,78 @@ +import { + aeAddress, + aeAmount, + aeBlockHash, + aeTxHash, + bigint, + index, + integer, + onchainTable, + text, +} from '@growae/aesync' + +export const token = onchainTable( + 'token', + { + address: aeAddress('address').primaryKey(), + name: text('name').notNull(), + daoAddress: aeAddress('dao_address').notNull(), + communityManagementAddress: aeAddress( + 'community_management_address', + ).notNull(), + createdAtHeight: integer('created_at_height').notNull(), + createdAtTx: aeTxHash('created_at_tx').notNull(), + }, + (table) => [index('token_name_idx').on(table.name)], +) + +export const transaction = onchainTable( + 'transaction', + { + id: integer('id').primaryKey().generatedAlwaysAsIdentity(), + tokenSaleAddress: aeAddress('token_sale_address').notNull(), + type: text('type').notNull(), // 'buy' | 'sell' + tokenAmount: aeAmount('token_amount').notNull(), + aeAmount: aeAmount('ae_amount').notNull(), + fee: aeAmount('fee'), + height: integer('height').notNull(), + blockHash: aeBlockHash('block_hash').notNull(), + txHash: aeTxHash('tx_hash').notNull(), + timestamp: bigint('timestamp', { mode: 'number' }).notNull(), + }, + (table) => [ + index('tx_token_sale_idx').on(table.tokenSaleAddress), + index('tx_height_idx').on(table.height), + ], +) + +export const priceChange = onchainTable( + 'price_change', + { + id: integer('id').primaryKey().generatedAlwaysAsIdentity(), + tokenSaleAddress: aeAddress('token_sale_address').notNull(), + oldPrice: aeAmount('old_price').notNull(), + newPrice: aeAmount('new_price').notNull(), + height: integer('height').notNull(), + txHash: aeTxHash('tx_hash').notNull(), + timestamp: bigint('timestamp', { mode: 'number' }).notNull(), + }, + (table) => [index('pc_token_sale_idx').on(table.tokenSaleAddress)], +) + +export const tokenDayData = onchainTable( + 'token_day_data', + { + id: text('id').primaryKey(), // `${tokenSaleAddress}-${date}` + tokenSaleAddress: aeAddress('token_sale_address').notNull(), + date: text('date').notNull(), // YYYY-MM-DD + dailyBuyCount: integer('daily_buy_count').notNull().default(0), + dailySellCount: integer('daily_sell_count').notNull().default(0), + dailyBuyVolume: aeAmount('daily_buy_volume').notNull().default('0'), + dailySellVolume: aeAmount('daily_sell_volume').notNull().default('0'), + price: aeAmount('price').notNull().default('0'), + }, + (table) => [ + index('tdd_token_sale_idx').on(table.tokenSaleAddress), + index('tdd_date_idx').on(table.date), + ], +) diff --git a/examples/bcl-indexer/src/api/index.ts b/examples/bcl-indexer/src/api/index.ts new file mode 100644 index 0000000..7362e32 --- /dev/null +++ b/examples/bcl-indexer/src/api/index.ts @@ -0,0 +1,68 @@ +import { db } from 'aesync:api' +import { aesync } from 'aesync:registry' +import { desc, eq, sql } from 'drizzle-orm' +import { priceChange, token, transaction } from '../../schema.js' + +aesync.get('/tokens', async (c: any) => { + const tokens = await db.select().from(token) + return c.json(tokens) +}) + +aesync.get('/tokens/:address', async (c: any) => { + const address = c.req.param('address') + const result = await db + .select() + .from(token) + .where(eq(token.address, address)) + .limit(1) + if (!result[0]) return c.json({ error: 'Token not found' }, 404) + return c.json(result[0]) +}) + +aesync.get('/tokens/:address/transactions', async (c: any) => { + const address = c.req.param('address') + const limit = Number(c.req.query('limit') ?? 50) + const txs = await db + .select() + .from(transaction) + .where(eq(transaction.tokenSaleAddress, address)) + .orderBy(desc(transaction.height)) + .limit(Math.min(limit, 200)) + return c.json(txs) +}) + +aesync.get('/tokens/:address/price-history', async (c: any) => { + const address = c.req.param('address') + const limit = Number(c.req.query('limit') ?? 50) + const prices = await db + .select() + .from(priceChange) + .where(eq(priceChange.tokenSaleAddress, address)) + .orderBy(desc(priceChange.height)) + .limit(Math.min(limit, 200)) + return c.json(prices) +}) + +aesync.get('/stats', async (c: any) => { + const [tokenCount] = await db + .select({ count: sql`count(*)` }) + .from(token) + const [buyCount] = await db + .select({ count: sql`count(*)` }) + .from(transaction) + .where(eq(transaction.type, 'buy')) + const [sellCount] = await db + .select({ count: sql`count(*)` }) + .from(transaction) + .where(eq(transaction.type, 'sell')) + const [priceChangeCount] = await db + .select({ count: sql`count(*)` }) + .from(priceChange) + + return c.json({ + totalTokens: tokenCount?.count ?? 0, + totalBuys: buyCount?.count ?? 0, + totalSells: sellCount?.count ?? 0, + totalPriceChanges: priceChangeCount?.count ?? 0, + }) +}) diff --git a/examples/bcl-indexer/src/factory.ts b/examples/bcl-indexer/src/factory.ts new file mode 100644 index 0000000..03b5bfc --- /dev/null +++ b/examples/bcl-indexer/src/factory.ts @@ -0,0 +1,29 @@ +import type { EventCallbackFn } from '@growae/aesync' +import { token } from '../schema.js' + +/** + * BclFactory:CreateCommunity handler. + * + * ACI: CreateCommunity(string, DAO, TokenSale, CommunityManagement) + * Decoded args: arg0 = name, arg1 = DAO address, arg2 = TokenSale address, arg3 = CommunityManagement address + */ +export const onCreateCommunity: EventCallbackFn = async ({ + event, + context, +}) => { + const name = event.args.arg0 as string + const daoAddress = event.args.arg1 as string + const tokenSaleAddress = event.args.arg2 as string + const communityManagementAddress = event.args.arg3 as string + + await context.db.insert(token).values({ + address: tokenSaleAddress, + name, + daoAddress, + communityManagementAddress, + createdAtHeight: event.height, + createdAtTx: event.txHash, + }) + + context.contracts.register('BclTokenSale', tokenSaleAddress) +} diff --git a/examples/bcl-indexer/src/index.ts b/examples/bcl-indexer/src/index.ts new file mode 100644 index 0000000..e06a75e --- /dev/null +++ b/examples/bcl-indexer/src/index.ts @@ -0,0 +1,8 @@ +import { aesync } from 'aesync:registry' +import { onCreateCommunity } from './factory.js' +import { onBuy, onPriceChange, onSell } from './token-sale.js' + +aesync.on('BclFactory:CreateCommunity', onCreateCommunity) +aesync.on('BclTokenSale:Buy', onBuy) +aesync.on('BclTokenSale:Sell', onSell) +aesync.on('BclTokenSale:PriceChange', onPriceChange) diff --git a/examples/bcl-indexer/src/token-sale.ts b/examples/bcl-indexer/src/token-sale.ts new file mode 100644 index 0000000..ef741eb --- /dev/null +++ b/examples/bcl-indexer/src/token-sale.ts @@ -0,0 +1,106 @@ +import type { EventCallbackFn } from '@growae/aesync' +import { sql } from 'drizzle-orm' +import { priceChange, transaction } from '../schema.js' + +function dateFromTimestamp(ts: number): string { + return new Date(ts).toISOString().slice(0, 10) +} + +/** + * BclTokenSale:Buy handler. + * + * ACI: Buy(int, int, int) + * Decoded args: arg0 = token amount, arg1 = AE cost, arg2 = fee + */ +export const onBuy: EventCallbackFn = async ({ event, context }) => { + const tokenAmount = BigInt(event.args.arg0 as string | bigint) + const aeCost = BigInt(event.args.arg1 as string | bigint) + const fee = BigInt(event.args.arg2 as string | bigint) + + await context.db.insert(transaction).values({ + tokenSaleAddress: event.contractId, + type: 'buy', + tokenAmount: tokenAmount.toString(), + aeAmount: aeCost.toString(), + fee: fee.toString(), + height: event.height, + blockHash: event.blockHash, + txHash: event.txHash, + timestamp: event.blockTime, + }) + + const date = dateFromTimestamp(event.blockTime) + const dayId = `${event.contractId}-${date}` + + await context.db.execute(sql` + INSERT INTO token_day_data (id, token_sale_address, date, daily_buy_count, daily_sell_count, daily_buy_volume, daily_sell_volume, price) + VALUES (${dayId}, ${event.contractId}, ${date}, 1, 0, ${tokenAmount.toString()}, '0', '0') + ON CONFLICT (id) DO UPDATE SET + daily_buy_count = token_day_data.daily_buy_count + 1, + daily_buy_volume = (CAST(token_day_data.daily_buy_volume AS numeric) + ${tokenAmount.toString()})::text + `) +} + +/** + * BclTokenSale:Sell handler. + * + * ACI: Sell(int, int) + * Decoded args: arg0 = token amount, arg1 = AE returned + */ +export const onSell: EventCallbackFn = async ({ event, context }) => { + const tokenAmount = BigInt(event.args.arg0 as string | bigint) + const aeReturn = BigInt(event.args.arg1 as string | bigint) + + await context.db.insert(transaction).values({ + tokenSaleAddress: event.contractId, + type: 'sell', + tokenAmount: tokenAmount.toString(), + aeAmount: aeReturn.toString(), + fee: null, + height: event.height, + blockHash: event.blockHash, + txHash: event.txHash, + timestamp: event.blockTime, + }) + + const date = dateFromTimestamp(event.blockTime) + const dayId = `${event.contractId}-${date}` + + await context.db.execute(sql` + INSERT INTO token_day_data (id, token_sale_address, date, daily_buy_count, daily_sell_count, daily_buy_volume, daily_sell_volume, price) + VALUES (${dayId}, ${event.contractId}, ${date}, 0, 1, '0', ${tokenAmount.toString()}, '0') + ON CONFLICT (id) DO UPDATE SET + daily_sell_count = token_day_data.daily_sell_count + 1, + daily_sell_volume = (CAST(token_day_data.daily_sell_volume AS numeric) + ${tokenAmount.toString()})::text + `) +} + +/** + * BclTokenSale:PriceChange handler. + * + * ACI: PriceChange(int, int) + * Decoded args: arg0 = old price, arg1 = new price + */ +export const onPriceChange: EventCallbackFn = async ({ event, context }) => { + const oldPrice = BigInt(event.args.arg0 as string | bigint) + const newPrice = BigInt(event.args.arg1 as string | bigint) + + await context.db.insert(priceChange).values({ + tokenSaleAddress: event.contractId, + oldPrice: oldPrice.toString(), + newPrice: newPrice.toString(), + height: event.height, + txHash: event.txHash, + timestamp: event.blockTime, + }) + + const date = dateFromTimestamp(event.blockTime) + const dayId = `${event.contractId}-${date}` + + await context.db.execute(sql` + INSERT INTO token_day_data (id, token_sale_address, date, daily_buy_count, daily_sell_count, daily_buy_volume, daily_sell_volume, price) + VALUES (${dayId}, ${event.contractId}, ${date}, 0, 0, '0', '0', ${newPrice.toString()}) + ON CONFLICT (id) DO UPDATE SET + price = ${newPrice.toString()} + `) +} diff --git a/examples/bcl-indexer/tsconfig.json b/examples/bcl-indexer/tsconfig.json new file mode 100644 index 0000000..212528a --- /dev/null +++ b/examples/bcl-indexer/tsconfig.json @@ -0,0 +1,14 @@ +{ + "compilerOptions": { + "target": "ES2021", + "module": "ESNext", + "moduleResolution": "Bundler", + "strict": true, + "esModuleInterop": true, + "skipLibCheck": true, + "resolveJsonModule": true, + "declaration": true, + "outDir": "dist" + }, + "include": ["src/**/*.ts", "schema.ts", "aesync.config.ts", "aesync-env.d.ts"] +} diff --git a/examples/grow-dex-indexer/aesync.config.ts b/examples/grow-dex-indexer/aesync.config.ts index 1824946..fb39950 100644 --- a/examples/grow-dex-indexer/aesync.config.ts +++ b/examples/grow-dex-indexer/aesync.config.ts @@ -6,7 +6,7 @@ import GrowRouterAci from './abis/GrowRouter.json' export default createConfig({ network: { name: 'mainnet', - mdwUrl: process.env.AE_MDW_URL ?? 'https://mainnet.aeternity.io/mdw/v3', + mdwUrl: process.env.AE_MDW_URL ?? 'https://mainnet.aeternity.io/mdw', mdwWsUrl: process.env.AE_MDW_WS_URL ?? 'wss://mainnet.aeternity.io/mdw/v3/websocket', diff --git a/packages/core/src/aci/aci.test.ts b/packages/core/src/aci/aci.test.ts index 575a5de..d6d4e10 100644 --- a/packages/core/src/aci/aci.test.ts +++ b/packages/core/src/aci/aci.test.ts @@ -211,11 +211,11 @@ describe('Event Hash', () => { expect(hash.length).toBe(32) }) - it('computes consistent hex hash', () => { + it('computes consistent base32hex hash', () => { const hex1 = eventHashHex('Swap') const hex2 = eventHashHex('Swap') expect(hex1).toBe(hex2) - expect(hex1).toHaveLength(64) + expect(hex1).toHaveLength(56) }) it('produces different hashes for different event names', () => { diff --git a/packages/core/src/aci/decoder.ts b/packages/core/src/aci/decoder.ts index 2c9353e..6d65f52 100644 --- a/packages/core/src/aci/decoder.ts +++ b/packages/core/src/aci/decoder.ts @@ -1,5 +1,45 @@ +import { createHash } from 'node:crypto' import type { AciEvent, SophiaType } from './types.js' +const BASE58_ALPHABET = + '123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz' + +function base58Encode(buf: Uint8Array): string { + let num = 0n + for (const b of buf) num = num * 256n + BigInt(b) + let out = '' + while (num > 0n) { + out = BASE58_ALPHABET[Number(num % 58n)] + out + num /= 58n + } + for (const b of buf) { + if (b === 0) out = `1${out}` + else break + } + return out +} + +/** + * Convert a decimal big-integer string from ae-mdw into an Aeternity + * address (`ak_`/`ct_`). Falls through to the raw string if it already + * looks like an ae address or is not a pure decimal. + */ +function decodeAddress(value: string): string { + if (/^(ak|ct|ok|nm|cm|ch|sg|ba|cb)_/.test(value)) return value + if (!/^\d+$/.test(value)) return value + + const bigint = BigInt(value) + const hex = bigint.toString(16).padStart(64, '0') + const payload = Buffer.from(hex, 'hex') + const h1 = createHash('sha256').update(payload).digest() + const h2 = createHash('sha256').update(h1).digest() + const checksum = h2.subarray(0, 4) + const full = new Uint8Array(36) + full.set(payload) + full.set(checksum, 32) + return `ct_${base58Encode(full)}` +} + function decodeValue(type: SophiaType, value: string): unknown { if (typeof type === 'string') { switch (type) { @@ -8,6 +48,7 @@ function decodeValue(type: SophiaType, value: string): unknown { case 'bool': return value !== '0' case 'address': + return decodeAddress(value) case 'hash': case 'signature': case 'bytes': diff --git a/packages/core/src/aci/hash.ts b/packages/core/src/aci/hash.ts index 6bc166f..c40fcee 100644 --- a/packages/core/src/aci/hash.ts +++ b/packages/core/src/aci/hash.ts @@ -1,11 +1,29 @@ import blakejs from 'blakejs' const encoder = new TextEncoder() +const BASE32HEX_CHARS = '0123456789ABCDEFGHIJKLMNOPQRSTUV' + +function toBase32Hex(bytes: Uint8Array): string { + let bits = '' + for (const b of bytes) bits += b.toString(2).padStart(8, '0') + while (bits.length % 5 !== 0) bits += '0' + let out = '' + for (let i = 0; i < bits.length; i += 5) { + out += BASE32HEX_CHARS[Number.parseInt(bits.substring(i, i + 5), 2)] + } + while (out.length % 8 !== 0) out += '=' + return out +} export function computeEventHash(eventName: string): Uint8Array { return blakejs.blake2b(encoder.encode(eventName), undefined, 32) } +/** + * Returns the blake2b-256 hash of the event name encoded as base32hex + * (RFC 4648 §7), matching the format ae-mdw uses for `event_hash`. + */ export function eventHashHex(eventName: string): string { - return blakejs.blake2bHex(encoder.encode(eventName), undefined, 32) + const hash = blakejs.blake2b(encoder.encode(eventName), undefined, 32) + return toBase32Hex(hash) } diff --git a/packages/core/src/aci/parser.ts b/packages/core/src/aci/parser.ts index 26e4b48..d950bc2 100644 --- a/packages/core/src/aci/parser.ts +++ b/packages/core/src/aci/parser.ts @@ -104,17 +104,32 @@ export function parseSophiaType(raw: unknown): SophiaType { return 'string' } +const INDEXABLE_TYPES: Set = new Set([ + 'int', + 'bool', + 'address', + 'hash', + 'signature', + 'bytes', +]) + +function isIndexable(t: SophiaType): boolean { + if (typeof t === 'string') return INDEXABLE_TYPES.has(t) + return false +} + function parseEvents(variant: Record[]): AciEvent[] { return variant.map((entry) => { const name = Object.keys(entry)[0]! const rawTypes = entry[name]! - const fields: AciEventField[] = rawTypes.map((rawType, i) => ({ - index: i, - name: `arg${i}`, - type: parseSophiaType(rawType), - indexed: i < MAX_INDEXED_FIELDS, - })) + let indexedCount = 0 + const fields: AciEventField[] = rawTypes.map((rawType, i) => { + const type = parseSophiaType(rawType) + const indexed = isIndexable(type) && indexedCount < MAX_INDEXED_FIELDS + if (indexed) indexedCount++ + return { index: i, name: `arg${i}`, type, indexed } + }) return { name, diff --git a/packages/core/src/bin/aesync.ts b/packages/core/src/bin/aesync.ts index 9bcc234..e5d15e0 100644 --- a/packages/core/src/bin/aesync.ts +++ b/packages/core/src/bin/aesync.ts @@ -9,7 +9,7 @@ import { registerServe } from './commands/serve.js' import { registerStart } from './commands/start.js' const require = createRequire(import.meta.url) -const pkg = require('../../package.json') as { version: string } +const pkg = require('../../../package.json') as { version: string } const program = new Command() diff --git a/packages/core/src/build/build.test.ts b/packages/core/src/build/build.test.ts index 9af3f19..2dde816 100644 --- a/packages/core/src/build/build.test.ts +++ b/packages/core/src/build/build.test.ts @@ -108,7 +108,7 @@ describe('Build System', () => { const result = await compileContracts(config) expect(result.size).toBe(1) - const pair = result.get('Pair')! + const pair = result.get('ct_pair123')! expect(pair.name).toBe('Pair') expect(pair.address).toBe('ct_pair123') expect(pair.events).toHaveLength(3) @@ -128,8 +128,8 @@ describe('Build System', () => { const result = await compileContracts(config) expect(result.size).toBe(2) - expect(result.get('Pair')!.events).toHaveLength(3) - expect(result.get('Token')!.events).toHaveLength(1) + expect(result.get('ct_pair')!.events).toHaveLength(3) + expect(result.get('ct_token')!.events).toHaveLength(1) }) it('throws on missing ACI', async () => { @@ -144,17 +144,18 @@ describe('Build System', () => { const result = await compileContracts(config) const transfer = result - .get('Token')! + .get('ct_token')! .events.find((e) => e.name === 'Transfer')! expect(transfer.hash).toBeDefined() - expect(transfer.hash).toHaveLength(64) + expect(transfer.hash).toHaveLength(56) }) it('defaults address to empty string when not provided', async () => { const config = makeConfig({ Token: { aci: TOKEN_ACI } }) const result = await compileContracts(config) - expect(result.get('Token')!.address).toBe('') + const token = result.get('Token')! + expect(token.address).toBe('') }) }) diff --git a/packages/core/src/build/contracts.ts b/packages/core/src/build/contracts.ts index dc624e0..9fac036 100644 --- a/packages/core/src/build/contracts.ts +++ b/packages/core/src/build/contracts.ts @@ -13,14 +13,19 @@ export async function compileContracts( } const parsed = parseAci(contractConfig.aci) + const address = contractConfig.address ?? '' - result.set(name, { + const compiled: CompiledContract = { name, - address: contractConfig.address ?? '', + address, aci: parsed, events: parsed.events, factory: contractConfig.factory, - }) + startHeight: contractConfig.startHeight, + endHeight: contractConfig.endHeight, + } + + result.set(address || name, compiled) } return result diff --git a/packages/core/src/build/index.ts b/packages/core/src/build/index.ts index 3b89d7f..9c310ee 100644 --- a/packages/core/src/build/index.ts +++ b/packages/core/src/build/index.ts @@ -1,3 +1,5 @@ +import { dirname, resolve } from 'node:path' +import { fileURLToPath } from 'node:url' import type { Table } from 'drizzle-orm' import type { PgTable } from 'drizzle-orm/pg-core/table' import { createServer as createViteServer } from 'vite' @@ -5,7 +7,10 @@ import { ViteNodeRunner } from 'vite-node/client' import { ViteNodeServer } from 'vite-node/server' import type { AeSyncConfig } from '../config/types.js' import { createDatabase } from '../database/index.js' -import { applyMigrations } from '../database/migrate.js' +import { + applyInternalMigrations, + applyMigrations, +} from '../database/migrate.js' import type { Database } from '../database/types.js' import { type MdwClient, createMdwClient } from '../mdw/index.js' import type { CompiledContract, EventCallback } from '../sync/types.js' @@ -43,9 +48,10 @@ export interface BuildOptions { export async function createBuild(options: BuildOptions): Promise { const { rootDir, watch = false, configPath, schemaPath } = options + const coreDir = resolve(dirname(fileURLToPath(import.meta.url)), '..', '..') const server = await createViteServer({ root: rootDir, - plugins: [vitePluginAeSync({ rootDir })], + plugins: [vitePluginAeSync({ rootDir, coreDir })], server: { hmr: watch }, logLevel: 'silent', }) @@ -71,9 +77,11 @@ export async function createBuild(options: BuildOptions): Promise { const schema = await compileSchema(runner, rootDir, schemaPath) const database = await createDatabase(config.database) + await applyInternalMigrations(database.qb) await applyMigrations(database.qb, schema as Record) const indexing = await compileIndexing(runner, rootDir, contracts) + ;(globalThis as Record).__AESYNC_DB__ = database.qb const api = await compileApi(runner, rootDir) await generateEnvDts(rootDir, contracts) diff --git a/packages/core/src/build/indexing.ts b/packages/core/src/build/indexing.ts index 62fcde2..69980b5 100644 --- a/packages/core/src/build/indexing.ts +++ b/packages/core/src/build/indexing.ts @@ -41,11 +41,11 @@ function validateHandlerName( ) } - const contract = contracts.get(contractName) + const contract = [...contracts.values()].find((c) => c.name === contractName) if (!contract) { throw new Error( `Handler "${name}" references unknown contract "${contractName}". ` + - `Available: ${[...contracts.keys()].join(', ')}`, + `Available: ${[...contracts.values()].map((c) => c.name).join(', ')}`, ) } diff --git a/packages/core/src/build/plugin.ts b/packages/core/src/build/plugin.ts index 97d5123..fc2a52d 100644 --- a/packages/core/src/build/plugin.ts +++ b/packages/core/src/build/plugin.ts @@ -1,3 +1,4 @@ +import { createRequire } from 'node:module' import { resolve } from 'node:path' import type { Plugin } from 'vite' @@ -8,7 +9,14 @@ const API_ID = 'aesync:api' const VIRTUAL_IDS = new Set([REGISTRY_ID, SCHEMA_ID, API_ID]) -export function vitePluginAeSync(options: { rootDir: string }): Plugin { +export function vitePluginAeSync(options: { + rootDir: string + coreDir?: string +}): Plugin { + const coreRequire = options.coreDir + ? createRequire(resolve(options.coreDir, 'package.json')) + : null + return { name: 'aesync', @@ -16,6 +24,13 @@ export function vitePluginAeSync(options: { rootDir: string }): Plugin { if (VIRTUAL_IDS.has(id)) { return VIRTUAL_PREFIX + id } + if (coreRequire && !id.startsWith('.') && !id.startsWith('/')) { + try { + return coreRequire.resolve(id) + } catch { + // fall through to default resolution + } + } return null }, diff --git a/packages/core/src/database/migrate.ts b/packages/core/src/database/migrate.ts index 0defd7d..fc8cc14 100644 --- a/packages/core/src/database/migrate.ts +++ b/packages/core/src/database/migrate.ts @@ -1,6 +1,11 @@ import { sql } from 'drizzle-orm' import { getTableConfig } from 'drizzle-orm/pg-core' import type { PgTable } from 'drizzle-orm/pg-core/table' +import { + aesyncCheckpoint, + aesyncContractState, + aesyncMeta, +} from '../schema/internal.js' import type { DrizzleInstance } from './types.js' function extractSqlString(chunks: unknown[]): string { @@ -99,6 +104,25 @@ function buildCreateIndexes(table: PgTable): string[] { return stmts } +export async function applyInternalMigrations( + qb: DrizzleInstance, +): Promise { + const internalTables: PgTable[] = [ + aesyncMeta, + aesyncContractState, + aesyncCheckpoint, + ] + for (const table of internalTables) { + const ddl = buildCreateTable(table) + await qb.execute(sql.raw(ddl)) + + const indexes = buildCreateIndexes(table) + for (const idx of indexes) { + await qb.execute(sql.raw(idx)) + } + } +} + export async function applyMigrations( qb: DrizzleInstance, tables: Record, diff --git a/packages/core/src/mdw/http.ts b/packages/core/src/mdw/http.ts index 3dc02fb..9eb9ec2 100644 --- a/packages/core/src/mdw/http.ts +++ b/packages/core/src/mdw/http.ts @@ -63,7 +63,7 @@ export function createMdwHttpClient( path: string, params?: URLSearchParams, ): Promise { - const url = new URL(path, base) + const url = new URL(`${base}${path}`) if (params) { for (const [k, v] of params) { url.searchParams.set(k, v) diff --git a/packages/core/src/sync/historical.ts b/packages/core/src/sync/historical.ts index bd6551a..8b8f797 100644 --- a/packages/core/src/sync/historical.ts +++ b/packages/core/src/sync/historical.ts @@ -22,18 +22,16 @@ export async function* createHistoricalSync( ): AsyncGenerator { let cursor = opts?.lastCursor - const scopeParts: string[] = [] - if (opts?.startHeight != null) { - scopeParts.push(`gen:${opts.startHeight}`) + const start = opts?.startHeight + const end = opts?.endHeight + let scope: string | undefined + if (start != null && end != null) { + scope = `gen:${start}-${end}` + } else if (start != null) { + scope = `gen:${start}-${start + 10_000_000}` + } else if (end != null) { + scope = `gen:0-${end}` } - if (opts?.endHeight != null) { - if (scopeParts.length > 0) { - scopeParts[0] = `${scopeParts[0]}-${opts.endHeight}` - } else { - scopeParts.push(`gen:0-${opts.endHeight}`) - } - } - const scope = scopeParts.length > 0 ? scopeParts[0] : undefined while (true) { const page: MdwPaginatedResponse = diff --git a/packages/core/src/sync/index.ts b/packages/core/src/sync/index.ts index 4a696c0..92b045f 100644 --- a/packages/core/src/sync/index.ts +++ b/packages/core/src/sync/index.ts @@ -144,7 +144,7 @@ export function createSync(params: CreateSyncParams): SyncEngine { try { const generator = createHistoricalSync(mdwHttp, contract, { lastCursor: state?.lastCursor, - startHeight: undefined, + startHeight: contract.startHeight, }) for await (const batch of generator) { @@ -192,9 +192,10 @@ export function createSync(params: CreateSyncParams): SyncEngine { }) } - const backfillPromises = [...contracts.values()].map((c) => - runBackfill(c), + const backfillContracts = [...contracts.values()].filter( + (c) => c.address !== '', ) + const backfillPromises = backfillContracts.map((c) => runBackfill(c)) await Promise.all(backfillPromises) if (stopped) return diff --git a/packages/core/src/sync/sync.test.ts b/packages/core/src/sync/sync.test.ts index e37eb4c..09b6129 100644 --- a/packages/core/src/sync/sync.test.ts +++ b/packages/core/src/sync/sync.test.ts @@ -312,7 +312,7 @@ describe('Historical Sync', () => { expect(mdw.getContractLogs).toHaveBeenCalledWith(CONTRACT_ID, { cursor: undefined, - scope: 'gen:500', + scope: 'gen:500-10000500', limit: 100, }) }) diff --git a/packages/core/src/sync/types.ts b/packages/core/src/sync/types.ts index 11d8318..1bbd6ac 100644 --- a/packages/core/src/sync/types.ts +++ b/packages/core/src/sync/types.ts @@ -49,6 +49,8 @@ export interface CompiledContract { aci: AciContract events: AciEvent[] factory?: FactoryConfig + startHeight?: number + endHeight?: number } export interface MatchedEvent { diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 113460f..965daa9 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -30,6 +30,12 @@ importers: specifier: ^3.0.0 version: 3.2.4(@types/node@25.6.0)(yaml@2.8.3) + examples/bcl-indexer: + dependencies: + '@growae/aesync': + specifier: workspace:* + version: link:../../packages/core + examples/grow-dex-indexer: dependencies: '@growae/aesync':