Local Development
This guide covers building Ironflow from source, running the development server, and developing SDKs locally.
Prerequisites
- Go 1.25+ (no CGO required)
- Node.js 20+ and pnpm
- Buf CLI (for protobuf generation) - Install Guide
- Docker (required for PostgreSQL and integration tests)
Building from Source
Clone the repository and build the binary:
git clone https://github.com/sahina/ironflow.gitcd ironflowmake allmake all runs the full pipeline: downloads dependencies, generates protobuf code, builds the React dashboard, embeds it into the Go binary, and compiles the final executable to ./build/ironflow.
Running the Dev Server
Build and start the server with SQLite (default):
make devThis starts the server at http://localhost:9123. For active frontend/SDK development, you’ll typically use three terminals:
- Server:
make dev— Core engine and API. - Dashboard:
cd apps/dashboard && pnpm dev— Vite dev server with HMR at:5173. - SDK Watch:
pnpm --filter "./sdk/js/*" dev— Rebuilds TypeScript packages on change.
Makefile Targets
| Target | Description |
|---|---|
make all | Full build: deps → embed → binary |
make build | Build the Go binary only |
make dev | Build everything and start dev server |
make proto | Generate Go/TS code from protobuf (requires Buf CLI) |
make test | Run all tests (Go, Go SDK, JS SDK, cloud-workflows) |
make test-go | Run Go tests (main module + Go SDK) |
make test-js | Run JS SDK tests only |
make test-pg | Run Go tests with PostgreSQL (requires Docker) |
make lint | Run golangci-lint on Go modules (main + SDK) |
make clean | Remove all build artifacts and caches |
Docker Compose Stack
Instead of building from source, you can run the full Ironflow stack using Docker Compose. The repository’s docker-compose.yml uses profiles to compose exactly the services you need.
Quick Start (SQLite + Metrics)
Build and start everything in one command:
docker compose --profile monitoring up --build -dThis starts Ironflow (with SQLite) and Prometheus. Check the logs for your admin credentials:
docker compose logs ironflowAvailable Profiles
| Profile | Services Added | Use Case |
|---|---|---|
| (none) | ironflow only | Minimal — SQLite, no monitoring |
postgres | ironflow + postgres | Production-like with PostgreSQL |
monitoring | ironflow + prometheus | Metrics and monitoring |
| Both | All three services | Full stack |
Profile Combinations
# Ironflow only (SQLite, no monitoring)docker compose up --build -d
# Ironflow + PostgreSQLdocker compose --profile postgres up --build -d
# Ironflow + Prometheusdocker compose --profile monitoring up --build -d
# Full stack: PostgreSQL + Prometheusdocker compose --profile postgres --profile monitoring up --build -dEnabling Observability
Prometheus metrics are enabled by default in Docker Compose (IRONFLOW_METRICS_ENABLED defaults to true in docker-compose.yml). When running outside Docker (e.g., make dev), metrics are off by default; set IRONFLOW_METRICS_ENABLED=true to enable. The /metrics endpoint is available when metrics are enabled, and Prometheus scrapes it automatically when the monitoring profile is active.
To also enable distributed tracing, set the OTel endpoint in a .env file:
# .env (optional, for distributed tracing)IRONFLOW_OTEL_ENDPOINT=localhost:4317Useful Commands
# View logsdocker compose logs -f ironflow
# Open Prometheus UI (when monitoring profile is active)open http://localhost:9090
# Stop all services (data preserved)docker compose --profile postgres --profile monitoring down
# Stop and delete all data (full reset)docker compose --profile postgres --profile monitoring down -v
# Rebuild after code changesdocker compose --profile monitoring up --build -dService Ports
| Service | Port | URL |
|---|---|---|
| Ironflow | 9123 | http://localhost:9123 |
| Ironflow Metrics | 9123 | http://localhost:9123/metrics |
| PostgreSQL | 5432 | 127.0.0.1:5432 (localhost only) |
| Prometheus | 9090 | http://localhost:9090 |
When to use Docker vs make dev
Use make dev when you’re actively developing Ironflow itself (Go code, dashboard, SDKs) — it provides faster iteration with hot-reload. Use Docker Compose when you want to test the full containerized stack, verify Docker builds, or run with PostgreSQL and Prometheus without installing them locally.
SDK Development
Ironflow is a monorepo. Changes to the core protocol (api/proto) must be propagated to the SDKs.
Protocol Changes
If you modify a .proto file in api/proto/ironflow/v1/:
- Run
make prototo regenerate the Go and TypeScript code. - Check
api/go/andsdk/js/core/src/gen/for the updated files.
JavaScript/TypeScript SDK (sdk/js/)
The JS SDK is a pnpm monorepo consisting of:
@ironflow/core: Generated types and shared logic.@ironflow/node: Worker and server-side utilities.@ironflow/browser: Browser-optimized client.@ironflow/langgraph: LangGraph checkpoint saver for durable agent state.
Workflow:
# Setupmake sdk-js-install
# Build and Testmake sdk-js-buildmake sdk-js-test
# Local iteration (watch mode)pnpm --filter "./sdk/js/*" devGo SDK (sdk/go/ironflow/)
The Go SDK is a standard Go module.
Workflow:
# Run testscd sdk/go/ironflowgo test -v ./...Testing SDKs in External Projects
To test your local changes in a real application without publishing to npm or GitHub:
JS SDK (using Tarballs)
-
Pack the SDK:
Terminal window make sdk-js-packThis creates
.tgzfiles in/tmp/ironflow-packs/. -
Install in your app:
Terminal window pnpm add file:/tmp/ironflow-packs/ironflow-node-<version>.tgz
Go SDK (using replace)
Add a replace directive to your application’s go.mod:
module my-app
go 1.25
require github.com/sahina/ironflow/sdk/go/ironflow v0.0.0
replace github.com/sahina/ironflow/sdk/go/ironflow => ../path/to/ironflow/sdk/go/ironflowTroubleshooting
”Bootstrap” Missing in Logs
The admin password and API key are only printed on the first run. If you missed them:
- Stop the server.
rm ironflow.db(for SQLite) ormake docker-reset-pg(for Postgres).- Restart the server.
Protobuf Generation Failures
If make proto fails, verify your Buf installation:
buf --version# Should support buf.yaml v2 format (buf >= 1.27)Database Lock (SQLite)
If you see database is locked, another Ironflow process is likely running. Use lsof -i :9123 to find and kill it.
Next Steps
- Architecture — Deep dive into the internal engine.
- ConnectRPC API — API protocol specifications.
- GitHub Issues — Pick up a “good first issue.”