Repository: sqlc-dev/sqlc
Stars: 17357
CLAUDE.md
Claude Code Development Guide for sqlc
This document provides essential information for working with the sqlc codebase, including testing, development workflow, and code structure.
Quick Start
Prerequisites
- Go 1.26.2+ - Required for building and testing
- Docker & Docker Compose - Required for integration tests with databases (local development)
- Git - For version control
Database Setup with sqlc-test-setup
The sqlc-test-setup tool (cmd/sqlc-test-setup/) automates installing and starting PostgreSQL and MySQL for tests. Both commands are idempotent and safe to re-run.
Install databases
go run ./cmd/sqlc-test-setup installThis will:
- Configure the apt proxy (if http_proxy is set, e.g. in Claude Code remote environments)
- Install PostgreSQL via apt
- Download and install MySQL 9 from Oracle's deb bundle
- Resolve all dependencies automatically
- Skip anything already installed
Start databases
go run ./cmd/sqlc-test-setup startThis will:
- Start PostgreSQL and configure password auth (postgres/postgres)
- Start MySQL via mysqld_safe and set root password (mysecretpassword)
- Verify both connections
- Skip steps that are already done (running services, existing config)
Connection URIs after start:
- PostgreSQL: postgres://postgres:[email protected]:5432/postgres?sslmode=disable
- MySQL: root:mysecretpassword@tcp(127.0.0.1:3306)/mysql
Run tests
Full test suite (requires databases running)
go test --tags=examples -timeout 20m ./...Running Tests
Basic Unit Tests (No Database Required)
go test ./...Full Test Suite with Docker (Local Development)
docker compose up -d
go test --tags=examples -timeout 20m ./...Full Test Suite without Docker (Remote / CI)
go run ./cmd/sqlc-test-setup install
go run ./cmd/sqlc-test-setup start
go test --tags=examples -timeout 20m ./...Running Specific Tests
Test a specific package
go test ./internal/configRun with verbose output
go test -v ./internal/configRun a specific test function
go test -v ./internal/config -run TestConfigRun with race detector (recommended for concurrency changes)
go test -race ./internal/configTest Types
1. Unit Tests
- Location: Throughout the codebase as *_test.go files
- Run without: Database or external dependencies
- Examples:
- /internal/config/config_test.go - Configuration parsing
- /internal/compiler/selector_test.go - Compiler logic
- /internal/metadata/metadata_test.go - Query metadata parsing
2. End-to-End Tests
- Location: /internal/endtoend/
- Requirements: --tags=examples flag and running databases
- Tests:
- TestExamples - Main end-to-end tests
- TestReplay - Replay tests
- TestFormat - Code formatting tests
- TestJsonSchema - JSON schema validation
- TestExamplesVet - Static analysis tests
3. Example Tests
- Location: /examples/ directory
- Requirements: Tagged with "examples", requires live databases
- Databases: PostgreSQL, MySQL, SQLite examples
Database Services
The docker-compose.yml provides test databases:
- PostgreSQL 16 - Port 5432
- User: postgres
- Password: mysecretpassword
- Database: postgres
- MySQL 9 - Port 3306
- User: root
- Password: mysecretpassword
- Database: dinotest
Makefile Targets
make test # Basic unit tests only
make test-examples # Tests with examples tag
make build-endtoend # Build end-to-end test data
make test-ci # Full CI suite (examples + endtoend + vet)
make vet # Run go vet
make start # Start database containersCI/CD Configuration
GitHub Actions Workflow
- File: .github/workflows/ci.yml
- Go Version: 1.26.2
- Database Setup: Uses sqlc-test-setup (not Docker) to install and start PostgreSQL and MySQL directly on the runner
- Test Command: gotestsum --junitfile junit.xml -- --tags=examples -timeout 20m ./...
- Additional Checks: govulncheck for vulnerability scanning
Development Workflow
Building Development Versions
Build main sqlc binary for development
go build -o ~/go/bin/sqlc-dev ./cmd/sqlcBuild JSON plugin (required for some tests)
go build -o ~/go/bin/sqlc-gen-json ./cmd/sqlc-gen-jsonEnvironment Variables for Tests
You can override database connections via environment variables:
POSTGRESQL_SERVER_URI="postgres://postgres:postgres@localhost:5432/postgres?sslmode=disable"
MYSQL_SERVER_URI="root:mysecretpassword@tcp(127.0.0.1:3306)/mysql?multiStatements=true&parseTime=true"Code Structure
Key Directories
- /cmd/ - Main binaries (sqlc, sqlc-gen-json, sqlc-test-setup)
- /internal/cmd/ - Command implementations (vet, generate, etc.)
- /internal/engine/ - Database engine implementations
- /postgresql/ - PostgreSQL parser and converter
- /dolphin/ - MySQL parser (uses TiDB parser)
- /sqlite/ - SQLite parser
- /internal/compiler/ - Query compilation logic
- /internal/codegen/ - Code generation for different languages
- /internal/config/ - Configuration file parsing
- /internal/endtoend/ - End-to-end tests
- /internal/sqltest/ - Test database setup (Docker, native, local detection)
- /examples/ - Example projects for testing
Important Files
- /Makefile - Build and test targets
- /docker-compose.yml - Database services for testing
- /.github/workflows/ci.yml - CI configuration
Common Issues & Solutions
Network Connectivity Issues
If you see errors about storage.googleapis.com, the Go proxy may be unreachable. Use GOPROXY=direct go mod download to fetch modules directly from source.
Test Timeouts
End-to-end tests can take a while. Use longer timeouts:
go test -timeout 20m --tags=examples ./...Race Conditions
Always run tests with the race detector when working on concurrent code:
go test -race ./...Database Connection Failures
If using Docker:
docker compose ps
docker compose up -dIf using sqlc-test-setup:
go run ./cmd/sqlc-test-setup startTips for Contributors
1. Run tests before committing: go test --tags=examples -timeout 20m ./...
2. Check for race conditions: Use -race flag when testing concurrent code
3. Use specific package tests: Faster iteration during development
4. Read existing tests: Good examples in /internal/engine/postgresql/*_test.go
Git Workflow
Branch Naming
- Feature branches should start with claude/ for Claude Code work
- Branch names should be descriptive and end with the session ID
Committing Changes
git add <files>
git commit -m "Brief description of changes"
git push -u origin <branch-name>Rebasing
git checkout main
git pull origin main
git checkout <feature-branch>
git rebase main
git push --force-with-lease origin <feature-branch>Resources
- Main Documentation: /docs/
- Development Guide: /docs/guides/development.md
- CI Configuration: /.github/workflows/ci.yml
- Docker Compose: /docker-compose.yml
README.md
sqlc: A SQL Compiler
!go

sqlc generates type-safe code from SQL. Here's how it works:
1. You write queries in SQL.
1. You run sqlc to generate code with type-safe interfaces to those queries.
1. You write application code that calls the generated code.
Check out an interactive example to see it in action, and the introductory blog post for the motivation behind sqlc.
Overview
- Documentation
- Installation
- Playground
- Website
- Downloads
- Community
Supported languages
- sqlc-gen-go
- sqlc-gen-kotlin
- sqlc-gen-python
- sqlc-gen-typescript
Additional languages can be added via plugins.
Sponsors
Development is possible thanks to our sponsors. If you would like to support sqlc,
please consider sponsoring on GitHub.
<p align="center">
<a href="https://riza.io?utm_source=sqlc+readme"><img width=400 src="https://sqlc.dev/sponsors/riza-readme.png" alt="Riza.io"></a>
</p>
<p align="center">
<a href="https://coder.com?utm_source=sqlc+readme"><img width=200 src="https://sqlc.dev/sponsors/coder-readme.png" alt="Coder.com" /></a>
<a href="https://mint.fun?utm_source=sqlc+readme"><img width=200 src="https://sqlc.dev/sponsors/mint-readme.png" alt="Mint.fun" /></a>
<a href="https://mux.com?utm_source=sqlc+readme"><img width=200 src="https://sqlc.dev/sponsors/mux-readme.png" alt="Mux.com" /></a>
</p>
<p align="center">
<a href="https://github.com/Cyberax">Cyberax</a> -
<a href="https://github.com/NaNuNaNu">NaNuNaNu</a> -
<a href="https://github.com/Stumble">Stumble</a> -
<a href="https://github.com/WestfalNamur">WestfalNamur</a> -
<a href="https://github.com/alecthomas">alecthomas</a> -
<a href="https://github.com/cameronnewman">cameronnewman</a> -
<a href="https://github.com/danielbprice">danielbprice</a> -
<a href="https://github.com/davherrmann">davherrmann</a> -
<a href="https://github.com/dvob">dvob</a> -
<a href="https://github.com/gilcrest">gilcrest</a> -
<a href="https://github.com/gzuidhof">gzuidhof</a> -
<a href="https://github.com/jeffreylo">jeffreylo</a> -
<a href="https://github.com/mmcloughlin">mmcloughlin</a> -
<a href="https://github.com/ryohei1216">ryohei1216</a> -
<a href="https://github.com/sgielen">sgielen</a>
</p>