Sim IDX provides a complete serverless API development environment with built-in database connectivity, automatic scaling, and edge deployment. Whether you’re building simple data endpoints or advanced features, the platform handles infrastructure concerns so you can focus on your business logic.

This guide walks you through the complete API development lifecycle on the platform.

Infrastructure & Scalability

Your API runs on Cloudflare Workers with the Hono framework. Anything you can do in Hono will also work here. Your data is stored in a Neon Postgres accessed through Cloudflare Hyperdrive. Requests execute at the edge close to users, and database connections are pooled automatically, so you don’t have to manage servers or connection limits.

The setup scales with your traffic, but there are sensible platform limits. If you anticipate sustained very high volume, please contact us so we can make sure everything runs smoothly.

Local Development Setup

Building APIs on Sim IDX follows a streamlined workflow: develop locally, write endpoints to query your indexed data, and deploy with a simple git push. The boilerplate API in the apis/ directory gives you a starting point with common patterns for querying your indexed blockchain data and serving it through HTTP endpoints.

Before deploying, you can run and test your API locally.

1

Navigate to the API directory

cd apis
2

Set Up Environment Variable

Create a file named .dev.vars in the apis/ directory. Add the database connection string, which you can find on the App Page after deploying your app for the first time.

.dev.vars
DB_CONNECTION_STRING="your_database_connection_string_from_app_page"
3

Install Dependencies

npm install
4

Start the Development Server

npm run dev

Your API is now running locally at http://localhost:8787.

Understand the API Code

The boilerplate API in apis/src/index.ts is a TypeScript application that runs on Cloudflare Workers. It connects to your indexed database and exposes HTTP endpoints to query your data. Let’s understand how this works:

Framework Setup

The API uses the sim-idx helper library, which wraps Hono and Drizzle to simplify setup:

import { App, db, types } from "sim-idx";
import { eq, sql } from "drizzle-orm";
import { poolCreated, ownerQueried } from "./db/schema/Listener";

Hono handles HTTP requests and routing, while Drizzle provides a type-safe way to query your PostgreSQL database.

Environment Configuration

sim-idx handles database credentials for you in both local development and deployed environments, so no additional environment variables are required.

Application Instance

Create the web application with a single call:

const app = App.create();

Database Connection Management

Instead of managing your own connection pool, call db.client(c) inside a request handler to reuse the shared Drizzle client:

const rows = await db.client(c)
  .select()
  .from(poolCreated)
  .limit(10);

Add a New Endpoint

Let’s build three endpoints to serve our indexed data:

  • /api/pools - Get recent Uniswap V3 pools
  • /api/owner-changed - Get recent owner changed events
  • /api/pools/count - Get total number of pools

Creating the Pools Endpoint

Let’s create our first endpoint to fetch the 10 most recent Uniswap V3 pools. This endpoint will query the pool_created table we created in our listener:

// Endpoint to get the 10 most recent Uniswap V3 pools
app.get("/api/pools", async (c) => {
  try {
    const rows = await db.client(c)
      .select()
      .from(poolCreated)
      .limit(10);

    return Response.json({ data: rows });
  } catch (e) {
    console.error("Database operation failed:", e);
    return Response.json({ error: (e as Error).message }, { status: 500 });
  }
});

This endpoint uses a simple SQL query to fetch the most recent pools. The LIMIT 10 clause ensures we don’t return too much data at once. In a production environment, you might want to add pagination and filtering options.

Adding the Owner Changed Endpoint

Before continuing, make sure you’ve added support for the OwnerChanged event in your listener contract by following the “Triggering more functions and events” section of the Listener guide and then running:

sim build

Running sim build regenerates apis/src/db/schema/Listener.ts with a new ownerChanged table binding that we import below.

Now let’s add an endpoint to fetch the 10 most recent owner changed events. This will query the owner_changed table:

// Endpoint to get the 10 most recent owner changed events
app.get("/api/owner-changed", async (c) => {
  try {
    const rows = await db.client(c)
      .select()
      .from(ownerChanged)
      .limit(10);

    return Response.json({ data: rows });
  } catch (e) {
    console.error("Database operation failed:", e);
    return Response.json({ error: (e as Error).message }, { status: 500 });
  }
});

Creating the Pool Count Endpoint

Finally, let’s add an endpoint to get the total number of pools. This will be useful for pagination and analytics:

// Endpoint to get the total number of pools
app.get("/api/pools/count", async (c) => {
  try {
    const [{ total }] = await db.client(c)
      .select({ total: sql<number>`COUNT(*)` })
      .from(poolCreated);

    return Response.json({ data: total });
  } catch (e) {
    console.error("Database operation failed:", e);
    return Response.json({ error: (e as Error).message }, { status: 500 });
  }
});

This endpoint uses an aggregate query to efficiently count pools without fetching every row.

Testing Your Endpoints

After adding all three endpoints, you can test them locally:

  • http://localhost:8787/api/pools - Get recent pools
  • http://localhost:8787/api/owner-changed - Get recent owner changed events
  • http://localhost:8787/api/pools/count - Get total pool count

Authenticate API Endpoints

Sim IDX provides built-in authentication middleware that integrates seamlessly with your app and the platform.

When deployed to production, the authentication middleware requires a valid Sim IDX App Endpoints API key to be passed with each request. Sim’s infrastructure validates the key and, if successful, allows the request to proceed. Unauthenticated requests will be rejected with a 401 Unauthorized error.

During local development, the authentication middleware automatically disables authentication checks when your API is running locally (i.e., when NODE_ENV is not production). This allows for a frictionless development experience without needing to manage API keys while testing your endpoints.

Create a Sim IDX App Endpoints API Key

Your API will need a Sim IDX App Endpoints API key to access your authenticated endpoints. They can generate a new key from the Sim dashboard.

To generate a new API key, visit the Keys page and click the New button.

When creating the key, its purpose should be set to Sim IDX App Endpoints. This key must be kept secure and should not be exposed in client-side code.

Understanding the Authentication Middleware

The authentication middleware is enabled by default in your API. When you create a new Sim IDX app, the boilerplate code in apis/src/index.ts already includes the necessary authentication setup:

apis/src/index.ts
import { App, db, types, middlewares } from "@duneanalytics/sim-idx";
import { eq, sql } from "drizzle-orm";
import { poolCreated, ownerChanged } from "./db/schema/Listener";

const app = App.create();

// Authentication middleware is applied to all routes by default
app.use("*", middlewares.authentication);

// Your endpoints...
app.get("/api/pools", async (c) => {
  // ...
});

export default app;

The middlewares.authentication is applied to all routes using the app.use("*", middlewares.authentication) line. This ensures that every endpoint in your API requires authentication when deployed.

Calling Your Authenticated API

Once your API is deployed, you must include their Sim IDX App Endpoints API key in the Authorization header with every request.

Here’s an example using cURL:

curl --request GET \
  --url https://<your-api-url>/api/pools \
  --header 'Authorization: Bearer YOUR_SIM_IDX_APP_ENDPOINTS_API_KEY'

Replace <your-api-url> with your deployment’s base URL and YOUR_SIM_IDX_APP_ENDPOINTS_API_KEY with a valid Sim IDX App Endpoints API key.

Deploy Your API

Once your repository is connected, shipping updates is as simple as pushing code:

  • Push commits to the main branch to roll out a new production deployment.
  • Push to any other branch to spin up a preview deployment with its own URL — perfect for staging and pull-request reviews.

Sim IDX automatically builds your Cloudflare Worker and updates the deployment status in the dashboard. No CLI command is required.