Configuring ENSIndexer
ENSIndexer requires private RPC endpoints. Public (rate limited) RPC endpoints will not provide acceptable performance.
You must configure private (paid) RPC services from providers like drpc.org, Alchemy, QuickNode, or Infura or host your own RPC service that can handle high-volume requests.
Warning: Configuring ENSIndexer to use the public ENSRainbow server (https://api.ensrainbow.io) will significantly slow down indexing.
For optimal indexing performance, always colocate ENSIndexer and ENSRainbow. For example, if you are running ENSIndexer locally, you should also run a local instance of ENSRainbow and set ENSRAINBOW_URL to your local ENSRainbow server.
ENSIndexer’s behavior can be configured through environment variables. Copy .env.local.example to .env.local and configure all required values.
# The port ENSIndexer serves its API on.# Optional. If this is not set, the default value is Ponder's default of 42069.# PORT=42069
# RPC configuration# Required. When ENSIndexer starts up it verifies RPCs are defined for each of the chains# that are to be indexed based on the configured NAMESPACE and PLUGINS, along with the ENS Root Chain.## NOTE: You must configure your own private RPC endpoints.# ENSIndexer makes millions of RPC requests during operation.# Public RPC endpoints are rate limited and will not provide acceptable performance.# You must use only private (paid) RPC endpoints or your own self-hosted RPC service# that is prepared to support millions of requests (ex: 500+ requests / second)## Each configured RPC endpoint must be prepared to receive and quickly# process millions of RPC requests. Private RPC service options include:# - drpc.org (paid plan) - https://drpc.org/# - Alchemy (paid plan) - https://www.alchemy.com/# - QuickNode (paid plan) - https://www.quicknode.com/# - Infura (paid plan) - https://infura.io/## The following environment variables are supported:# - ALCHEMY_API_KEY — if set, Alchemy RPC URLs (HTTP & WS) will be provided for each of the chains it supports# - DRPC_API_KEY — if set, an DRPC RPC URL (HTTP) will be provided for each of the chains it supports# - RPC_URL_${chainId} — specific, per-chain RPC settings (see below).## If RPC_URL_${chainId} is specified, that value will take precedence over the automatic RPC URLs# from Alchemy or DRPC. If both Alchemy and DRPC API Keys are specified, ENSIndexer will provide# both to Ponder, which will balance requests between them (see below).## For chain-specific RPC configuration, use the RPC_URL_{chainId} environment variable.# Its value is a comma-separated list of one or more HTTP RPC URLs and at most one WebSocket RPC URL.## Example (single HTTP RPC URL):# RPC_URL_1=https://eth-mainnet.g.alchemy.com/v2/YOUR_API_KEY## Example (multiple HTTP RPC URL, single WebSocket RPC URL):# RPC_URL_1=https://eth-mainnet.g.alchemy.com/v2/YOUR_API_KEY,https://lb.drpc.org/ethereum/YOUR_API_KEY,wss://eth-mainnet.g.alchemy.com/v2/YOUR_API_KEY## The RPC_URL_${chainId} value has the following invariants:# - Must always include at least one HTTP/HTTPS RPC endpoint. RPC endpoints can# fail or experience downtime. To optimize resiliency of ENSIndexer,# defining more than one HTTP/HTTPS endpoint (from more than one RPC provider)# per indexed chain is strongly encouraged.# - Can include at most one WS/WSS (websocket) RPC endpoint. A WS/WSS (websocket)# RPC endpoint per indexed chain is optional. If defined it may optimize# the time to discover new blocks. Independent of a websocket RPC endpoint# being defined, Ponder automatically polls the HTTP/HTTPS RPC endpoint for# a chain to discover new blocks at an interval.## To optimize performance, Ponder automatically adapts to the rate limits (429 errors) of each# provided HTTP/HTTPS RPC. More details at: https://ponder.sh/docs/config/chains#rpc-endpoints#
# === ENS Namespace: Mainnet ===# Ethereum Mainnet# - required if the configured namespace is mainnet# - required by plugins: subgraph, protocol-acceleration, registrars, tokenscopeRPC_URL_1=
# Optimism Mainnet# - required by plugins: threedns, protocol-acceleration, tokenscopeRPC_URL_10=
# Base Mainnet# - required by plugins: basenames, threedns, protocol-acceleration, registrars, tokenscopeRPC_URL_8453=
# Arbitrum Mainnet# - required by plugins: protocol-accelerationRPC_URL_42161=
# Linea Mainnet# - required by plugins: lineanames, protocol-acceleration, registrars, tokenscopeRPC_URL_59144=
# Scroll Mainnet# - required by plugins: protocol-accelerationRPC_URL_534352=
# === ENS Namespace: Sepolia ===# Ethereum Sepolia (public testnet)# - required if the configured namespace is sepolia# - required by plugins: subgraph, protocol-acceleration, registrars, tokenscopeRPC_URL_11155111=
# Base Sepolia (public testnet)# - required by plugins: basenames, protocol-acceleration, registrars, tokenscopeRPC_URL_84532=
# Linea Sepolia (public testnet)# - required by plugins: lineanames, protocol-acceleration, registrars, tokenscopeRPC_URL_59141=
# Optimism Sepolia (public testnet)# - required by plugins: protocol-acceleration, tokenscopeRPC_URL_11155420=
# Arbitrum Sepolia (public testnet)# - required by plugins: protocol-accelerationRPC_URL_421614=
# Scroll Sepolia (public testnet)# - required by plugins: protocol-accelerationRPC_URL_534351=
# === ENS Namespace: Holesky ===# Ethereum Holesky (public testnet)# - required if the configured namespace is holesky# - required by plugins: subgraph, protocol-acceleration, tokenscopeRPC_URL_17000=
# === ENS Namespace: ens-test-env ===# ens-test-env (local testnet)# - required if the configured namespace is ens-test-envRPC_URL_1337=
# Database configuration# Required. This is a namespace for the tables that the indexer will create to store indexed data.# It should be a string that is unique to the running indexer instance.## Keeping the database schema unique to the indexer instance is important to# 1) speed up indexing after a restart# 2) prevent data corruption from multiple indexer app instances writing state# concurrently to the same db schema## No two indexer instances can use the same database schema at the same time.## Read more about database schema rules here:# https://ponder.sh/docs/api-reference/database#database-schema-rules## Avoid using the `public` schema as we force that in the `dev` command. Using `public`# cause conflicts as you interchange between dev and start commands so use literally# anything else.DATABASE_SCHEMA=production# Required. This is the connection string for the database that the indexer will use to store data.# It should be in the format of `postgresql://<username>:<password>@<host>:<port>/<database>`DATABASE_URL=postgresql://dbuser:abcd1234@localhost:5432/my_database
# ENS Namespace Configuration# Required. Must be an ENS namespace's Identifier such as mainnet, sepolia, holesky,# or ens-test-env. (see `@ensnode/datasources` for available options).NAMESPACE=mainnet
# Plugin Configuration# Required. Identify which indexer plugins to activate (see `src/plugins` for available plugins)# This is a comma separated list of one or more available plugin names (case-sensitive).# NOTE:# - for subgraph-compatible indexing, the only valid configuration is `PLUGINS=subgraph`.# - to support Protocol Acceleration in the Resolution API, enable the protocol-acceleration plugin.PLUGINS=subgraph,basenames,lineanames,threedns,protocol-acceleration,registrars,tokenscope
# ENSRainbow service URL# Required. This is the URL of the ENSRainbow server that ENSIndexer will use to heal# unknown labels. The best indexing performance requires a colocated deployments of# ENSIndexer and ENSRainbow services to minimize latency. For example, both services should# communicate over the same local network.# Read more about ENSRainbow here:# https://ensrainbow.io# If you need to temporarily use the public ENSRainbow server for testing, set the following:# ENSRAINBOW_URL=https://api.ensrainbow.io (NOT RECOMMENDED - WILL MAKE INDEXING VERY SLOW!!)ENSRAINBOW_URL=http://localhost:3223
# Pinned Label Set Configuration for requests to ENSRainbow# Required. ENSIndexer must be pinned to a specific label set ID and version to ensure deterministic# indexing results across time.## For a list of available label sets and their configurations, visit:# https://ensnode.io/ensrainbow/usage/available-label-sets/## LABEL_SET_ID: The label set identifier that will be used for label healing requests sent to ENSRainbow.# Each label set id references a collection of rainbow records.# This must match the label set ID configured in your ENSRainbow server.## For full subgraph backwards compatibility, LABEL_SET_ID must be set to "subgraph"# and LABEL_SET_VERSION must be set to 0.LABEL_SET_ID=subgraph
# LABEL_SET_VERSION: A non-negative integer representing the version of the label set to request from ENSRainbow.# This "fully pins" ENSIndexer to a deterministic set of ENSRainbow label healing responses across time,# even if the connected ENSRainbow later ingests additional records into the same label set.# This must be less than or equal to the label set version configured in your ENSRainbow server.## For full subgraph backwards compatibility, LABEL_SET_ID must be set to "subgraph"# and LABEL_SET_VERSION must be set to 0.LABEL_SET_VERSION=0
# The "primary" ENSIndexer service URL# Required. This must be an instance of ENSIndexer using either `ponder start` or `ponder dev`,# (not `ponder serve`). This URL is used to read Ponder's internal indexing state to power the Config# and Indexing Status APIs. This should be configured so that ENSIndexer refers back to itself.# ex: http://localhost:{port}.ENSINDEXER_URL=http://localhost:42069
# A feature flag to enable/disable ENSIndexer's Subgraph Compatible Indexing Behavior# Optional. If this is not set, the default value is set to `DEFAULT_SUBGRAPH_COMPAT` (false).## When SUBGRAPH_COMPAT is true, ENSIndexer will:# 1. Interpret the Literal Labels and Literal Names encountered as Subgraph Interpreted Labels / Names# - https://ensnode.io/docs/reference/terminology#subgraph-interpreted-label# - https://ensnode.io/docs/reference/terminology#subgraph-interpreted-name# 2. Apply the following default configuration, which can be overridden:# - PLUGINS=subgraph# - LABEL_SET_ID=subgraph# - LABEL_SET_VERSION=0## Note: If SUBGRAPH_COMPAT is true but the resulting config is not Subgraph Compatible, an invariant will# be thrown.## When SUBGRAPH_COMPAT is false (default), ENSIndexer will:# 1. Interpret the Literal Labels and Literal Names encountered as Interpreted Labels / Names# - https://ensnode.io/docs/reference/terminology#interpreted-label# - https://ensnode.io/docs/reference/terminology#interpreted-name# 2. Heal all subnames of addr.reverse on the ENS Root Chain# 3. Apply the following default configuration, which can be overridden:# - PLUGINS=subgraph,basenames,lineanames,threedns# - LABEL_SET_ID=subgraph# - LABEL_SET_VERSION=0## SUBGRAPH_COMPAT=false