ArchAPI
ArchAPI is a Python library and CLI for architecture-preserving REST API generation.
Instead of generating API code from a generic template or an LLM's default style, ArchAPI studies your existing backend project first — its framework, folder conventions, naming style, authentication and validation patterns — and generates new API layers that match it. Generation is a dry-run preview by default; nothing is written to disk unless you explicitly ask for it.
Two generation modes:
- Deterministic — rule-based templates, works fully offline.
- LLM-assisted (
--llm) — an LLM writes the code, guided by an architecture-aware retrieval pipeline that selects and shows the model the repository examples most relevant to your specific request (not arbitrary or first-found files) — see Architecture.
Dedicated framework support: Express TypeScript, FastAPI, Flask, Django REST Framework, NestJS (anything else falls back to a generic, lower-confidence adapter).
Current version: 1.0.0 (see Development Status)
Installation from PyPI
python -m pip install archapi
To use LLM-first generation mode, install the optional openai extra:
python -m pip install "archapi[openai]"
Verify:
python -c "from archapi import ArchAPI; print('ArchAPI import works')"
Run from GitHub Source
git clone https://github.com/rohith5005/archapi.git
cd archapi
python3 -m venv .venv
source .venv/bin/activate
python -m pip install --upgrade pip setuptools wheel
python -m pip install -e .
Verify:
python -c "from archapi import ArchAPI; print('GitHub source install worked')"
Run Tests
python -m compileall archapi evaluation
python -m unittest discover -s tests -v
Or:
./scripts/run_tests.sh
Expected result:
Ran 231 tests
OK
No OPENAI_API_KEY is required — the full suite never makes a real network call.
Quickstart
pip install archapi
archapi scan .
archapi plan . "Create authenticated POST API for warranty claim"
# dry-run by default
archapi generate . "Create authenticated POST API for warranty claim"
# LLM-assisted, still dry-run -- retrieval selects the repository examples
# most relevant to this request (see docs/ARCHITECTURE.md)
archapi generate . "Create authenticated POST API for warranty claim" --llm
# explicit mutation -- always opt-in
archapi generate . "Create authenticated POST API for warranty claim" --llm --apply
Full CLI reference (all commands, flags, exit codes): docs/CLI.md.
Basic Usage (Python API)
from archapi import ArchAPI
engine = ArchAPI("./sample_projects/express_basic")
result = engine.generate_api(
"Create GET API for invoice",
dry_run=True,
)
print(result.plan)
print(result.validation_report)
print(result.diff)
Command-Line Interface
archapi detect ./sample_projects/express_basic
archapi scan ./sample_projects/express_basic
archapi plan ./sample_projects/express_basic "Create GET API for shipment status"
archapi generate ./sample_projects/express_basic "Create GET API for shipment status"
# Architecture-aware LLM generation instead of deterministic templates
archapi generate ./sample_projects/express_basic "Create GET API for shipment status" --llm
# Write files to disk instead of a dry run -- always opt-in, always explicit
archapi generate ./sample_projects/express_basic "Create GET API for shipment status" --llm --apply
# Machine-readable output for CI/tooling (any command)
archapi generate ./sample_projects/express_basic "Create GET API for shipment status" --json
generate is a dry-run preview by default; nothing is written to disk unless
--apply is passed. Exit codes are stable and documented: 0 success, 1
generation/validation rejected, 2 invalid CLI usage or configuration, 3
LLM provider failure. Pass --debug for full tracebacks on unexpected
errors; without it, errors are concise and never include credentials.
Configuration
Settings resolve with precedence: explicit CLI flag > project archapi.toml
environment variable > built-in default (full detail:
docs/CONFIGURATION.md). Optional project-localarchapi.toml:
[archapi]
use_llm = true
strict_validation = false
[archapi.llm]
provider = "openai"
model = "gpt-4o-mini"
[archapi.retrieval]
max_chars = 12000
routes = 2
services = 2
schemas = 2
tests = 2
API keys are never read from archapi.toml (ArchAPI refuses to load a
config file containing a key-, secret-, token-, password-, or
credential-like key) -- only from the OPENAI_API_KEY environment
variable. Equivalent environment variables exist for every field (e.g.
ARCHAPI_USE_LLM, ARCHAPI_LLM_MODEL, ARCHAPI_ROUTES_LIMIT) -- see
archapi/config.py.
LLM-First Generation (optional)
With the openai extra installed and OPENAI_API_KEY set, ArchAPI can use an
LLM to generate architecture-matching code instead of the deterministic
templates. See LLM Usage Guide for the full walkthrough.
from archapi import ArchAPI
engine = ArchAPI(
"./sample_projects/express_basic",
use_llm=True,
llm_model="gpt-4o-mini",
)
result = engine.generate_api(
"Create authenticated POST API for warranty claim",
dry_run=True,
)
print(result.plan)
print(result.validation_report)
Deterministic generation (use_llm=False, the default) does not require the
openai package and works fully offline.
How architecture-aware retrieval works
On the LLM path, ArchAPI doesn't send the model arbitrary or first-found
repository files. It indexes the project, scores every candidate file
against the specific request (resource, HTTP method, whether auth/validation
was asked for), and sends a budgeted set of the highest-relevance examples —
a route or two, a service, a schema, an auth example only if authentication
was requested, a test — labeled so the model knows what each one
demonstrates. See docs/ARCHITECTURE.md for the
full pipeline and docs/RESEARCH_REPORT.md for
the evidence this actually changes what gets generated.
Safety mechanisms
Dry-run by default, atomic multi-file application with automatic rollback
on partial failure, path-traversal/absolute-path rejection, project-root
containment, protected-file/bootstrap-file controls, generated-secret
detection, framework validation, and context redaction before any content
leaves the machine. No --skip-safety-style bypass exists. Full detail:
docs/SECURITY_MEASURES.md.
Express TypeScript Example
from pathlib import Path
from archapi import ArchAPI
project = Path("express_basic")
(project / "src/routes").mkdir(parents=True, exist_ok=True)
(project / "src/controllers").mkdir(parents=True, exist_ok=True)
(project / "src/services").mkdir(parents=True, exist_ok=True)
(project / "src/schemas").mkdir(parents=True, exist_ok=True)
(project / "tests").mkdir(parents=True, exist_ok=True)
(project / "package.json").write_text(
'{"dependencies": {"express": "^4.18.0", "zod": "^3.0.0"}}'
)
(project / "src/routes/user.routes.ts").write_text(
'import { Router } from "express";\n'
'const router = Router();\n'
'export default router;\n'
)
(project / "src/controllers/user.controller.ts").write_text(
'export const userController = {};\n'
)
(project / "src/services/user.service.ts").write_text(
'export const userService = {};\n'
)
(project / "src/schemas/user.schema.ts").write_text(
'import { z } from "zod";\n'
)
(project / "tests/user.test.ts").write_text(
'describe("user", () => { it("works", () => expect(true).toBe(true)); });\n'
)
engine = ArchAPI(str(project))
result = engine.generate_api("Create GET API for user order history", dry_run=True)
print("Detected framework:", engine.detect_framework().framework)
print("Generated method:", result.plan.method)
print("Generated path:", result.plan.path)
print("Generated files:", [str(file.path) for file in result.files])
Expected output includes:
Detected framework: express-typescript
Generated method: GET
Generated path: /users/{user_id}/orders
FastAPI Example
from pathlib import Path
from archapi import ArchAPI
project = Path("fastapi_basic")
(project / "app/routers").mkdir(parents=True, exist_ok=True)
(project / "app/services").mkdir(parents=True, exist_ok=True)
(project / "app/schemas").mkdir(parents=True, exist_ok=True)
(project / "tests").mkdir(parents=True, exist_ok=True)
(project / "requirements.txt").write_text("fastapi\npydantic\npytest\n")
(project / "app/routers/user_router.py").write_text(
"from fastapi import APIRouter\n"
"router = APIRouter()\n"
)
(project / "app/services/user_service.py").write_text(
"class UserService:\n"
" pass\n\n"
"user_service = UserService()\n"
)
(project / "app/schemas/user_schema.py").write_text(
"from pydantic import BaseModel\n\n"
"class UserResponse(BaseModel):\n"
" id: str\n"
)
(project / "tests/test_user.py").write_text(
"def test_user_placeholder():\n"
" assert True\n"
)
engine = ArchAPI(str(project))
result = engine.generate_api("Create POST API for product review", dry_run=True)
print("Detected framework:", engine.detect_framework().framework)
print("Generated method:", result.plan.method)
print("Generated path:", result.plan.path)
print("Generated files:", [str(file.path) for file in result.files])
Expected output includes:
Detected framework: fastapi
Generated method: POST
Generated path: /products/{product_id}/reviews
Documentation
- How to Run
- Architecture
- Configuration
- CLI Reference
- LLM Usage Guide
- Security Measures
- Evaluation Harness
- Research Report
- Development Status
- File Guide
Contributors
Links
Metadata
Release files for archapi 1.0.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | Actions |
|---|---|---|---|---|
| archapi-1.0.0.tar.gz | 94.7 kB | Without provenance | Details for archapi-1.0.0.tar.gz |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Actions Reset |
|---|---|---|---|---|
| archapi-1.0.0-py3-none-any.whl | Python 3 | none | any | Details for archapi-1.0.0-py3-none-any.whl |
Total release size: 170.0 kB
Release files / archapi-1.0.0.tar.gz
| Download URL | archapi-1.0.0.tar.gz |
|---|---|
| Size | 94.7 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
f1cacbc3a0d14b9b3c398047ae0847d5f43c1d4ac8103a6e7313e1b91adf11ec
|
|
BLAKE2b-256 checksum How to use checksums |
6df7606c95aba8942ff6eaec7390a92fdd5144b357563abd908c49285ddea22c
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.13.9
|
Release files / archapi-1.0.0-py3-none-any.whl
| Download URL | archapi-1.0.0-py3-none-any.whl |
|---|---|
| Size | 75.4 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
a8eadc53e3944d63a1df273f0e10cd1648f85e9bfce155e54c11a07a7694a046
|
|
BLAKE2b-256 checksum How to use checksums |
e2b5bbfda76bb281a74666b9f91ad1d925a569c30383c16a2b94e28c4e8586bf
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.13.9
|
Security for archapi 1.0.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
No provenance found
None of the files in this release were uploaded with provenance metadata.
A note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.