Skip to content

Commit 99be045

Browse files
committed
Improve contributor workflow
1 parent bbdfd08 commit 99be045

6 files changed

Lines changed: 271 additions & 4 deletions

File tree

.github/workflows/template-ci.yml

Lines changed: 87 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,90 @@ on:
66
- main
77
pull_request:
88

9+
permissions:
10+
contents: read
11+
912
jobs:
10-
verify:
13+
contract-drift:
14+
name: Contract Drift
1115
runs-on: ubuntu-latest
16+
steps:
17+
- name: Checkout
18+
uses: actions/checkout@v4
19+
20+
- name: Setup Node
21+
uses: actions/setup-node@v4
22+
with:
23+
node-version-file: .nvmrc
24+
cache: npm
25+
cache-dependency-path: package-lock.json
26+
27+
- name: Install root tooling
28+
run: npm ci
29+
30+
- name: Verify generated API types
31+
run: npm run check:contract
32+
33+
frontend:
34+
name: Frontend
35+
runs-on: ubuntu-latest
36+
steps:
37+
- name: Checkout
38+
uses: actions/checkout@v4
39+
40+
- name: Setup Node
41+
uses: actions/setup-node@v4
42+
with:
43+
node-version-file: .nvmrc
44+
cache: npm
45+
cache-dependency-path: frontend/package-lock.json
46+
47+
- name: Install frontend dependencies
48+
run: npm ci
49+
working-directory: frontend
50+
51+
- name: Lint frontend
52+
run: npm run lint:strict
53+
working-directory: frontend
54+
55+
- name: Typecheck frontend
56+
run: npm run typecheck
57+
working-directory: frontend
58+
59+
- name: Build frontend
60+
run: npm run build
61+
working-directory: frontend
62+
63+
backend:
64+
name: Backend
65+
runs-on: ubuntu-latest
66+
steps:
67+
- name: Checkout
68+
uses: actions/checkout@v4
69+
70+
- name: Setup Python
71+
uses: actions/setup-python@v5
72+
with:
73+
python-version: "3.12"
74+
cache: pip
75+
cache-dependency-path: backend/pyproject.toml
76+
77+
- name: Install backend dependencies
78+
run: |
79+
python -m pip install --upgrade pip
80+
python -m pip install -e ./backend[dev]
81+
82+
- name: Run backend tests
83+
run: python -m pytest
84+
working-directory: backend
85+
86+
- name: Compile backend package
87+
run: python -m compileall app
88+
working-directory: backend
89+
90+
root-check-windows:
91+
name: Root Check (Windows)
92+
runs-on: windows-latest
1293
steps:
1394
- name: Checkout
1495
uses: actions/checkout@v4
@@ -26,6 +107,8 @@ jobs:
26107
uses: actions/setup-python@v5
27108
with:
28109
python-version: "3.12"
110+
cache: pip
111+
cache-dependency-path: backend/pyproject.toml
29112

30113
- name: Install root tooling
31114
run: npm ci
@@ -39,8 +122,8 @@ jobs:
39122
python -m pip install --upgrade pip
40123
python -m pip install -e ./backend[dev]
41124
42-
- name: Generate API types
43-
run: npm run api:types
125+
- name: Verify generated API types
126+
run: npm run check:contract
44127

45-
- name: Run template checks
128+
- name: Run root verification
46129
run: npm run check

AGENTS.md

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
# AGENTS
2+
3+
Guidance for coding agents working in this repository.
4+
5+
## Repo Intent
6+
7+
This repo is a product-minded starter for computer-vision apps.
8+
9+
The default story is:
10+
11+
1. upload an image
12+
2. run a detection-first inference pipeline
13+
3. inspect typed detections, metrics, and image metadata
14+
4. extend into segmentation or webcam capture without changing the contract boundary
15+
16+
Keep that shape intact when making changes.
17+
18+
## Repo Map
19+
20+
- `frontend/`: Next.js app, upload flow, webcam flow, docs preview routes, generated API types
21+
- `backend/`: FastAPI service, pipeline registry, validation, response schemas, tests
22+
- `docs/openapi.yaml`: source of truth for the API contract
23+
- `frontend/src/generated/openapi.ts`: generated types from the OpenAPI spec
24+
- `scripts/dev.mjs`: root dev runner for frontend + backend
25+
- `scripts/check.mjs`: root verification entrypoint
26+
- `scripts/check-contract-drift.mjs`: ensures generated API types match the spec
27+
28+
## Working Rules
29+
30+
- Prefer detection-first, inference-first changes over adding disconnected demo paths.
31+
- Keep frontend and backend loosely coupled through the API contract, not direct assumptions.
32+
- If you change response payloads or request shapes, update `docs/openapi.yaml`, regenerate types, and verify both sides.
33+
- Treat `frontend/src/app/docs-preview/` as docs-only seeded demo pages for README screenshots. They should stay stable and lightweight.
34+
- Do not commit `node_modules`, `.venv`, `.next`, caches, or local-only helper files.
35+
36+
## Contract Change Checklist
37+
38+
When changing the API contract:
39+
40+
1. update `docs/openapi.yaml`
41+
2. update backend schemas and route behavior
42+
3. run `npm run api:types`
43+
4. update frontend usage if generated types changed
44+
5. run `npm run check`
45+
46+
## Verification
47+
48+
Use these commands before finishing work:
49+
50+
```bash
51+
npm run check:contract
52+
npm run check
53+
```
54+
55+
## Frontend Note
56+
57+
This repo uses Next.js 16. Do not assume older App Router behavior is still correct. Check current Next.js docs or the local Next.js bundled docs when making framework-sensitive changes.
58+
59+
## Backend Note
60+
61+
The backend sample logic is intentionally CPU-first and easy to replace. Prefer keeping model-specific logic behind the small vision service boundary rather than leaking it into routes.

CONTRIBUTING.md

Lines changed: 89 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,89 @@
1+
# Contributing
2+
3+
Thanks for contributing to the computer-vision kit.
4+
5+
## Prerequisites
6+
7+
- Node.js 22+
8+
- Python 3.12+
9+
- Git
10+
11+
## First-Time Setup
12+
13+
1. Install root dependencies:
14+
15+
```bash
16+
npm install
17+
```
18+
19+
2. Install frontend dependencies:
20+
21+
```bash
22+
cd frontend
23+
npm install
24+
cd ..
25+
```
26+
27+
3. Install backend dependencies:
28+
29+
```bash
30+
python -m pip install -e ./backend[dev]
31+
```
32+
33+
4. Generate frontend types from the API contract:
34+
35+
```bash
36+
npm run api:types
37+
```
38+
39+
## Local Development
40+
41+
Run both apps from the repo root:
42+
43+
```bash
44+
npm run dev
45+
```
46+
47+
Frontend: `http://localhost:3000`
48+
Backend: `http://127.0.0.1:8000`
49+
50+
If `backend/.venv` exists, the root scripts will prefer that interpreter automatically.
51+
52+
## Verification
53+
54+
Run these before opening a pull request:
55+
56+
```bash
57+
npm run check:contract
58+
npm run check
59+
```
60+
61+
What they cover:
62+
63+
- `check:contract`: regenerates frontend API types and fails if generated files drift from `docs/openapi.yaml`
64+
- `check`: frontend lint, frontend typecheck, frontend production build, backend tests, backend bytecode compile
65+
66+
## Changing the API Contract
67+
68+
If you modify request or response shapes:
69+
70+
1. update `docs/openapi.yaml`
71+
2. update backend schemas and implementation
72+
3. run `npm run api:types`
73+
4. update frontend usage of the generated types
74+
5. run `npm run check:contract`
75+
6. run `npm run check`
76+
77+
## Repo Conventions
78+
79+
- Keep the main story detection-first.
80+
- Reuse the same inference contract for upload, webcam, and later extensions.
81+
- Keep model-specific logic behind the backend vision service boundary.
82+
- Treat `frontend/src/app/docs-preview/` as docs-only seeded preview routes used for README screenshots.
83+
84+
## Pull Request Notes
85+
86+
- Keep changes scoped and explain user-facing impact clearly.
87+
- Mention contract changes explicitly.
88+
- Include screenshots when UI behavior changes.
89+
- Add or update tests when backend behavior changes.

README.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ It gives you a polished upload-to-inference UI, a typed OpenAPI contract, CPU-fr
88
<a href="#quick-start">Quick start</a> ·
99
<a href="#screenshots">Screenshots</a> ·
1010
<a href="#what-you-get">What you get</a> ·
11+
<a href="./CONTRIBUTING.md">Contributing</a> ·
1112
<a href="./soon.md">Roadmap</a>
1213
</p>
1314

@@ -91,6 +92,7 @@ If you create `backend/.venv`, the root scripts will prefer that interpreter aut
9192
npm run dev
9293
npm run dev:down
9394
npm run api:types
95+
npm run check:contract
9496
npm run check
9597
```
9698

@@ -109,6 +111,7 @@ The root check runs:
109111
- `docs/openapi.yaml` is the source of truth for the HTTP contract.
110112
- `frontend/src/generated/openapi.ts` is generated from that spec.
111113
- Run `npm run api:types` whenever backend payloads change.
114+
- Run `npm run check:contract` to confirm the generated types are committed and in sync.
112115

113116
## Recommended Growth Path
114117

package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
"dev": "node scripts/dev.mjs",
77
"dev:down": "docker compose down",
88
"api:types": "openapi-typescript ./docs/openapi.yaml -o ./frontend/src/generated/openapi.ts",
9+
"check:contract": "node scripts/check-contract-drift.mjs",
910
"check": "node scripts/check.mjs"
1011
},
1112
"keywords": [

scripts/check-contract-drift.mjs

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
import { spawnSync } from "node:child_process";
2+
import process from "node:process";
3+
4+
const commands = [
5+
{
6+
command: "npm",
7+
args: ["run", "api:types"],
8+
},
9+
{
10+
command: "git",
11+
args: ["diff", "--exit-code", "--", "frontend/src/generated/openapi.ts"],
12+
},
13+
];
14+
15+
for (const item of commands) {
16+
const result = spawnSync(item.command, item.args, {
17+
stdio: "inherit",
18+
shell: process.platform === "win32",
19+
});
20+
21+
if (result.status !== 0) {
22+
if (item.command === "git") {
23+
console.error(
24+
"Generated API types are out of date. Run `npm run api:types` and commit the updated file.",
25+
);
26+
}
27+
28+
process.exit(result.status ?? 1);
29+
}
30+
}

0 commit comments

Comments
 (0)