{"id":50664336,"url":"https://github.com/iotexproject/iotex-analyser","last_synced_at":"2026-06-08T05:01:12.290Z","repository":{"id":351765853,"uuid":"347544791","full_name":"iotexproject/iotex-analyser","owner":"iotexproject","description":"async analyser for iotex","archived":false,"fork":false,"pushed_at":"2026-06-01T00:44:44.000Z","size":2385,"stargazers_count":2,"open_issues_count":15,"forks_count":0,"subscribers_count":2,"default_branch":"main","last_synced_at":"2026-06-01T01:14:20.351Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/iotexproject.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":"SECURITY.md","support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2021-03-14T04:37:48.000Z","updated_at":"2026-06-01T00:44:00.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/iotexproject/iotex-analyser","commit_stats":null,"previous_names":["iotexproject/iotex-analyser"],"tags_count":249,"template":false,"template_full_name":null,"purl":"pkg:github/iotexproject/iotex-analyser","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/iotexproject%2Fiotex-analyser","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/iotexproject%2Fiotex-analyser/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/iotexproject%2Fiotex-analyser/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/iotexproject%2Fiotex-analyser/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/iotexproject","download_url":"https://codeload.github.com/iotexproject/iotex-analyser/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/iotexproject%2Fiotex-analyser/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34048682,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-08T02:00:07.615Z","response_time":111,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2026-06-08T05:00:47.332Z","updated_at":"2026-06-08T05:01:12.218Z","avatar_url":"https://github.com/iotexproject.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# IoTeX Analyser\n\n[![License: Apache 2.0](https://img.shields.io/badge/License-Apache_2.0-blue.svg)](LICENSE)\n[![Go Report Card](https://goreportcard.com/badge/github.com/iotexproject/iotex-analyser)](https://goreportcard.com/report/github.com/iotexproject/iotex-analyser)\n[![Latest Release](https://img.shields.io/github/v/release/iotexproject/iotex-analyser)](https://github.com/iotexproject/iotex-analyser/releases)\n[![Docker Image](https://img.shields.io/badge/ghcr.io-iotexproject%2Fiotex--analyser-blue?logo=docker)](https://github.com/iotexproject/iotex-analyser/pkgs/container/iotex-analyser)\n\n**IoTeX Analyser** indexes data from the [IoTeX blockchain](https://iotex.io) into the database of your choice (PostgreSQL, MySQL, SQLite, ClickHouse) and exposes it for downstream querying — including a managed GraphQL endpoint via Hasura.\n\nIt is built around a **dynamic plugin system**: indexing logic ships as Go plugins (`.so` files) that can be loaded and unloaded at runtime, with no service restart. A growing library of [58+ built-in plugins](plugins/) covers common needs (blocks, actions, ERC20/721/1155, staking, rewards, gas tracking, account income, …), and you can drop in your own.\n\n![Technical architecture](docs/assets/images/162696321861.png)\n\n---\n\n## Table of Contents\n\n- [Quick Start](#quick-start)\n- [Configuration](#configuration)\n- [Building from Source](#building-from-source)\n- [Running the Server](#running-the-server)\n- [Plugin System](#plugin-system)\n  - [Writing a Plugin](#writing-a-plugin)\n  - [Loading and Unloading at Runtime](#loading-and-unloading-at-runtime)\n- [GraphQL API](#graphql-api)\n- [Releases](#releases)\n- [Contributing](#contributing)\n- [License](#license)\n\n---\n\n## Quick Start\n\nThe fastest way to try Analyser is via Docker Compose, which provisions both Postgres and the Analyser service:\n\n```sh\ndocker-compose up\n```\n\nTo use a prebuilt image directly:\n\n```sh\ndocker pull ghcr.io/iotexproject/iotex-analyser:latest\n```\n\nAvailable image tags:\n- `:latest` — latest tagged release (recommended)\n- `:vX.Y.Z` — pinned release version\n- `:main` — bleeding edge from `main`\n- `:sha-\u003cshort\u003e` — exact commit\n\n---\n\n## Configuration\n\nAnalyser is configured via a YAML file. A minimal `config.yml`:\n\n```yaml\nserver:\n  # Plugins to load on startup\n  plugins:\n    - block.so\n\ndatabase:\n  driver: postgres        # postgres | mysql | sqlite3 | clickhouse\n  host: 127.0.0.1\n  port: 5432\n  user: postgres\n  password: ${DB_PASSWORD}\n  name: iotex\n\niotex:\n  chainEndPoint: api.iotex.one:80   # mainnet (use api.testnet.iotex.one:80 for testnet)\n\nblockDB:\n  dbPath: chain.db\n\nlog:\n  zap:\n    level: info\n```\n\n\u003e **Note:** Never commit real credentials. Use environment variable substitution (`${VAR}`) or a separate untracked config file.\n\n### Bootstrapping with a Snapshot\n\nIndexing from genesis takes time. Speed it up with a pre-indexed `chain.db` snapshot:\n\n- **Mainnet:** https://t.iotex.me/mainnet-data-with-idx-latest\n- **Testnet:** https://t.iotex.me/testnet-data-with-idx-latest\n\nDrop the file at the path referenced by `blockDB.dbPath` and Analyser will resume from the snapshot.\n\n---\n\n## Building from Source\n\n### Requirements\n\n- Go 1.23+\n- `make`\n- A working C linker (plugins use `-buildmode=plugin`, which requires glibc — Alpine without `gcompat` won't work for local builds)\n\n### Build\n\nClone and build the binary plus all plugins:\n\n```sh\ngit clone https://github.com/iotexproject/iotex-analyser.git\ncd iotex-analyser\nmake            # binary + every plugin under plugins/\n```\n\nOr build individual targets:\n\n```sh\nmake build              # binary only\nmake plugin name=block  # one plugin (produces block.so)\nmake dev                # binary + all plugins with -race for development\n```\n\n---\n\n## Running the Server\n\nStart the server:\n\n```sh\n./iotex-analyser -c config.yml server\n```\n\nManage plugins at runtime via a second process (the running server picks up changes automatically):\n\n```sh\n./iotex-analyser -c config.yml plugin load   simple.so\n./iotex-analyser -c config.yml plugin unload simple.so\n./iotex-analyser -c config.yml plugin info\n```\n\n---\n\n## Plugin System\n\nEach plugin is a Go package compiled to a `.so` file with `-buildmode=plugin`, exposing a single `Plugin` variable that satisfies the `Adapter` interface:\n\n```go\ntype Adapter interface {\n    Name() string\n    Version() string\n    Type() Type\n    Start(context.Context) error\n    Stop(context.Context) error\n    PutBlock(context.Context, *block.Block) error\n}\n```\n\nFor better throughput, plugins may also implement `PutBlocks(ctx, []*block.Block) error` to process blocks in batches.\n\n### Writing a Plugin\n\n```go\npackage main\n\nimport (\n    \"context\"\n    \"fmt\"\n\n    \"github.com/iotexproject/iotex-analyser/db\"\n    \"github.com/iotexproject/iotex-analyser/plugin\"\n    \"github.com/iotexproject/iotex-core/v2/blockchain/block\"\n)\n\ntype simplePlugin struct{}\n\nfunc (simplePlugin) Name() string         { return \"simple\" }\nfunc (simplePlugin) Version() string      { return \"0.0.1\" }\nfunc (simplePlugin) Type() plugin.Type    { return plugin.TypeStandard }\nfunc (simplePlugin) Start(context.Context) error { return nil }\nfunc (simplePlugin) Stop(context.Context) error  { return nil }\n\nfunc (s simplePlugin) PutBlock(ctx context.Context, blk *block.Block) error {\n    fmt.Printf(\"block height: %d\\n\", blk.Height())\n    return db.UpdateIndexHeight(s.Name(), blk.Height())\n}\n\n// Exported symbol — must be named \"Plugin\".\nvar Plugin = simplePlugin{}\n```\n\nBuild it:\n\n```sh\nmake plugin name=simple\n```\n\n### Loading and Unloading at Runtime\n\n```sh\n./iotex-analyser -c config.yml plugin load   simple.so\n./iotex-analyser -c config.yml plugin unload simple.so\n```\n\nAfter `load`, you should see output from your plugin in the server logs, e.g.:\n\n```\nblock height: 1\nblock height: 2\nblock height: 3\n```\n\n### Built-in Plugins\n\nA non-exhaustive sample — see [`plugins/`](plugins/) for the full list:\n\n- **Core blocks/actions:** [block](plugins/block/), [block_action](plugins/block_action/), [block_meta](plugins/block_meta/), [block_supply](plugins/block_supply/), [block_receipts](plugins/block_receipts/)\n- **Tokens:** [erc20](plugins/erc20/), [erc721](plugins/erc721/), [erc1155](plugins/erc1155/), token holder/meta variants\n- **Staking \u0026 delegation:** [candidate](plugins/candidate/), [staking_action](plugins/staking_action/), [delegate](plugins/delegate/), [probation](plugins/probation/)\n- **Accounting:** [account_meta](plugins/account_meta/), [account_income](plugins/account_income/), [account_vote](plugins/account_vote/)\n- **Other:** [gastracker](plugins/gastracker/), [erc1967_proxy](plugins/erc1967_proxy/), [clickhouse](plugins/clickhouse/) sinks\n\n---\n\n## GraphQL API\n\n[Hasura](https://hasura.io/) sits in front of the indexed Postgres database and serves a GraphQL API automatically.\n\n- **Hasura Console:** https://iotexscout.io/hasura/console\n- **GraphQL endpoint:** https://iotexscout.io/hasura/v1/graphql\n\n---\n\n## Releases\n\nReleases are cut manually using [`release.sh`](release.sh):\n\n```sh\n./release.sh v1.18.1\n```\n\nThe script validates the working tree, tags the commit, pushes the tag, and creates a GitHub Release with auto-generated notes. The tag push triggers GitHub Actions to build and publish the Docker image as both `:vX.Y.Z` and `:latest` on `ghcr.io`.\n\n---\n\n## Contributing\n\nContributions are welcome. The general flow:\n\n1. Open an issue to discuss non-trivial changes before starting work.\n2. Fork and create a feature branch.\n3. Add tests for new functionality where possible.\n4. Open a PR against `main`.\n\nUseful commands while developing:\n\n```sh\nmake dev          # build with -race for local testing\ngo test ./...     # run unit tests\n```\n\n---\n\n## License\n\nApache License 2.0 — see [LICENSE](LICENSE).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fiotexproject%2Fiotex-analyser","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fiotexproject%2Fiotex-analyser","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fiotexproject%2Fiotex-analyser/lists"}