Skip to main content

Gluo: PHP REST API Starter

Gluo logo

Gluo (Esperanto for glue) is a production-ready PHP REST API starter: create a project you fully own, powered by an updatable framework core — so you focus on business logic, not infrastructure.

Sponsor Build Status Opensource ByJG Install MCP Server GitHub source GitHub license GitHub release

Why Use This?​

Every new REST API needs the same boilerplate: authentication, migrations, an ORM, OpenAPI docs, a test harness, and a DI container. Setting all of that up correctly takes days — and it's not the work your users care about.

Gluo splits the problem the right way:

  • Your project (composer create-project byjg/gluo) — a full-stack monorepo: the PHP REST API at the repository root, an optional Vite + React frontend in frontend/, plus docker-compose.yml and docker/. Generated once, renamed to your namespace, fully yours: change, remove, or replace anything.
  • The framework core (byjg/gluo-core) — base classes, auth flow, attributes, code generator, and test harness live in vendor/ and improve with a plain composer update. No copy-paste to stay current.

And the API contract is never out of date: the OpenAPI attributes on your controllers generate openapi.json, which is at the same time the routing table and the contract every test checks responses against. An endpoint that is not documented does not exist, and a response that drifts from the documentation fails the test suite.

Quick Start​

# Create your project (the installer asks a few questions — see below)
composer create-project byjg/gluo my-api ^7.0

# Start containers (API, the database server, and the frontend if you kept it)
cd my-api
docker compose up -d

# Run migrations
php gluo --env=dev migrate:reset

# Your API is ready!
curl http://localhost:8080/sample/ping

Commands like php gluo migrate:update, php gluo codegen:all, php gluo openapi, php gluo test, and composer psalm run from the repository root — there is a single composer.json, and the repository root is the PHP application root.

What you get​

my-api/
├── composer.json # the single manifest (the repo root is the PHP app root)
├── src/ # Model, Repository, Service, Controller
├── config/ # dev / test / staging / prod
├── db/ # migrations + base.sql
├── public/ # the docroot: app.php, OpenAPI docs
├── templates/ # email + scriptify templates
├── tests/
├── frontend/ # optional Vite + React frontend (React 19 + Vite 6 + Tailwind)
├── docker/ # Dockerfile (API) + Dockerfile-html (frontend)
├── docker-compose.yml # API :8080, frontend :7080 (HTTPS :7443); includes the next file
├── docker-compose.database.yml # the database server (MySQL :3306, PostgreSQL :5432; none for SQLite)
└── README.md # quick start + link to the online documentation

The create-project installer offers two toggles:

  • Install Frontend — keep the frontend/ SPA (login, password-reset, dashboard, and profile screens, wired to the API over JWT). Say no and frontend/, its Docker image, and the frontend compose service are removed, leaving a pure API project.
  • Install Examples — keep the demo entities (Project, Task, Note) and their frontend pages. Say no and you get a clean app shell (auth + profile only, no example CRUD).
Install Examples: YesInstall Examples: No
Frontend: YesFull-stack demo (auth + example CRUD)Auth-only app shell (login/profile)
Frontend: NoPure API with example endpointsPure API, clean slate

When the frontend is enabled, docker compose up -d serves it at http://localhost:7080 and, with a self-signed certificate, at https://localhost:7443 (via byjg/static-httpserver) while the API answers on http://localhost:8080. See the Frontend guide →.

📚 Complete Getting Started Guide →

Architecture Overview​

Key Features​

  • 🚀 Code generator — one command scaffolds Model, Repository, Service, REST controller, and tests from any database table
  • 🏗️ Two patterns — choose Repository (DI + Service layer) or ActiveRecord per entity; mix them in the same project
  • 🔐 Auth out of the box — JWT login, token refresh, password reset, and role-based access control (RBAC) included
  • 📖 OpenAPI-first — routes are driven by openapi.json; the API reference (Scalar), contract testing, and docs stay in sync automatically
  • 🗄️ Database migrations — versioned up/down SQL migrations with a one-command runner and ORM integration
  • 🧪 In-process testing — FakeApiRequester runs the full API stack inside PHPUnit, no web server needed
  • 🎨 Optional React frontend — a Vite + React 19 + Tailwind SPA in frontend/ with login, password-reset, dashboard, and profile screens already wired to the API over JWT
  • 🐳 Docker ready — MySQL, PHP-FPM, Nginx, and the frontend pre-configured; docker compose up -d and you're running
  • 🔄 Updatable core — framework fixes and features arrive with composer update byjg/gluo-core; your code stays untouched
  • ⚙️ PSR standards — PSR-7 (HTTP messages), PSR-11 (container), PSR-6/16 (cache)
# Generate a complete CRUD API from a single table (run from the repo root)
php gluo --env=dev codegen:all --table=project --save

Documentation​

Getting Started​

  1. Installation & Setup – Install the starter, configure environments, and review prerequisites.
  2. Coming from another PHP framework (Laravel, Symfony, Drupal, CakePHP, CodeIgniter) – Concept and command mapping, plus the four things that genuinely work differently.
  3. Create Your First Table – Define your first migration and schema.
  4. Add Fields – Safely evolve existing tables.
  5. Create REST Endpoints – Generate REST handlers from your tables.
  6. Windows Setup – WSL/Windows-specific checklist.
  7. Unattended Setup – Automate installs for CI/CD pipelines.

Guides​

  • Frontend (Vite + React) – Run and customize the optional frontend/ SPA that talks to the API over JWT.
  • REST Controllers – Define routes with PHP attributes; keep controllers thin.
  • Authentication – Configure JWT login flows and RBAC enforcement.
  • Database Migrations – Version and run schema migrations in every environment.
  • ORM – Use MicroORM for repository and ActiveRecord patterns.
  • Service Layer – Organize business logic, orchestration, and transaction boundaries.
  • Repository Patterns – Implement complex queries, UUID handling, and filtering helpers.
  • Template Customization – Tailor the generator templates to match your coding standards.
  • Testing – Unit, integration, and contract testing with FakeApiRequester.
  • JWT Authentication Advanced – Extend tokens with custom claims and refresh logic.
  • Error Handling – Map exceptions to HTTP responses and logging patterns.
  • Configuration – Layer configurations, secrets, and environment overrides.

Concepts​

  • Architecture – Architectural decisions: when to use Repository vs ActiveRecord.
  • OpenAPI Integration – How swagger-php, the spec file, and the API reference fit together.
  • Dependency Injection – PSR-11 container, environment hierarchy, and DI binding patterns.
  • Request Lifecycle – Trace an HTTP request from entry point to JSON response.

Reference​

  • Code Generator – Automate models, repositories, services, controllers, and tests.
  • Attributes – RequireAuthenticated, RequireRole, ValidateRequest, and custom attributes.
  • Traits – Timestamp and soft-delete helpers for models.
  • The gluo Command – php gluo: migrations, codegen, OpenAPI, and your own project commands.
  • Scriptify – REPL, CLI runner, and service manager utilities.
  • Components – Full PHP component dependency graph.

AI coding agents​

gluo-developer is an Agent Skill that teaches a coding agent how a Gluo project is built: the two model patterns, codegen, the OpenAPI attributes, tests, migrations and the DI config. It is published at opensource.byjg.com/docs/ai/agent-skills/gluo-developer.

  • Claude Code: a project created from the starter declares the ByJG plugin catalog in .claude/settings.json, so Claude Code offers the skill once you trust the project folder. To install it by hand: /plugin marketplace add byjg/skills, then /plugin install gluo-developer@byjg.
  • Other agents that read Agent Skills (Codex, Cursor, Gemini CLI, ...): npx skills add byjg/skills --skill gluo-developer.

Real-World Example​

# 1. Create database table (migrations live under db/)
cat > db/migrations/up/00002-create-products.sql << 'EOF'
CREATE TABLE products (
id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(100) NOT NULL,
price DECIMAL(10,2) NOT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
EOF

# 2. Run migration
php gluo --env=dev migrate:update

# 3. Generate all code
php gluo --env=dev codegen:all --table=products --save

# 4. Generate the OpenAPI spec so routing is active
php gluo openapi

# 5. Log in and capture the token
TOKEN=$(curl -s -X POST http://localhost:8080/login \
-H "Content-Type: application/json" \
-d '{"username":"[email protected]","password":"!P4ssw0rdstr!"}' \
| jq -r '.token')

# 6. Call your new endpoint
curl -s -H "Authorization: Bearer $TOKEN" http://localhost:8080/products | jq

You just created a complete CRUD API with:

  • ✅ Model with validation
  • ✅ Repository for data access
  • ✅ Service for business logic
  • ✅ REST controller with GET, POST, PUT endpoints
  • ✅ Functional tests
  • ✅ OpenAPI documentation
  • ✅ JWT authentication

Requirements​

  • PHP 8.3+ (8.5 recommended)
  • Docker & Docker Compose (optional but recommended)
  • Composer
  • Git

Support & Community​

Your Code vs. the Framework​

The starter generates a project that is fully yours — src/, config/, db/, frontend/, docker/:

  • ✅ Full control over every file the generator gave you
  • ✅ Base classes are thin extension points (BaseLoginController, BaseRepository, BaseService, …) — override what you need
  • ✅ Framework improvements arrive via composer update byjg/gluo-core
  • ✅ Remove what you don't need — the frontend, auth, examples, and patterns are all optional

License​

This project is open source. See LICENSE for details.

Dependencies​

📚 Complete Component Dependency Graph →

Running Tests​

In this repository, docker-compose.yml, docker-compose.database.yml, db/base.sql and db/migrations/ are not versioned: they are written from .db-dialects/ for one database. A created project gets them as its own files.

composer install
php gluo --env=dev db:dialect mysql # or postgres, sqlite
docker compose up -d --wait
php gluo test

See the testing guide for writing tests for your own endpoints.


Open source ByJG