Compare commits
127 Commits
98ef35b532
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
c0cb013f54 | ||
|
|
dfe248ea5f | ||
|
|
ff775e3b8a | ||
|
|
0e51630439 | ||
|
|
bd0e9e4a20 | ||
|
|
c5972b9f04 | ||
|
|
e1b6cba1d4 | ||
|
|
0ff42c3c70 | ||
|
|
a6a9046457 | ||
|
|
40ae75808c | ||
|
|
fbede956e9 | ||
|
|
3793fca65e | ||
|
|
78d0eaa739 | ||
|
|
180ed41e68 | ||
|
|
ce2c90070e | ||
|
|
de63e9f216 | ||
|
|
7187631ebc | ||
|
|
5fa78fbdf6 | ||
|
|
f85ff79a2c | ||
|
|
a3ec7d63f2 | ||
|
|
9d5a463d93 | ||
|
|
d958933250 | ||
|
|
4aa7ba5d9b | ||
|
|
272a25fb05 | ||
|
|
d9411eb00e | ||
|
|
78ad32e93a | ||
|
|
d6e176bcd9 | ||
|
|
8d59f09cb2 | ||
|
|
30317326ce | ||
|
|
1fe35a2ea6 | ||
|
|
cd0f33f603 | ||
|
|
8b429be857 | ||
|
|
49d7f860de | ||
|
|
39c5a89ca7 | ||
|
|
ade2128a73 | ||
|
|
e5b354e322 | ||
|
|
be672b6ca9 | ||
|
|
a580314583 | ||
| 92a30b11db | |||
| fcee0f9213 | |||
| 4ca35de7ef | |||
| ad1c09f139 | |||
| 2b82d1918b | |||
| 8a047e8d9f | |||
|
|
03ca966708 | ||
|
|
b64c42ebde | ||
| c825d99b0a | |||
| cd5fd2d998 | |||
| e738fe484a | |||
| 31da1d557c | |||
| bfd45842fe | |||
|
|
6a44afd6b6 | ||
|
|
c380bebdd6 | ||
|
|
93e0d089f9 | ||
|
|
77c3407792 | ||
|
|
fe83c47e37 | ||
|
|
63d195ddf7 | ||
|
|
f06f4bf3a9 | ||
|
|
3c0ca485b8 | ||
|
|
1a7267ca4a | ||
|
|
b61a440994 | ||
|
|
f433b21bc1 | ||
| 1031a76099 | |||
| df160f1f72 | |||
| de1e9ac02b | |||
|
|
b27b5bdb40 | ||
|
|
30cdb48491 | ||
|
|
37667db2f6 | ||
|
|
f665df578c | ||
|
|
f9acdc8ada | ||
|
|
19dfad5ab5 | ||
|
|
633550f808 | ||
|
|
2b69c99d54 | ||
|
|
1f43f48276 | ||
|
|
9862d1cff4 | ||
|
|
c9a02dbedf | ||
|
|
d469c07250 | ||
|
|
76380d32c3 | ||
|
|
7162244454 | ||
|
|
b2095e7bdd | ||
|
|
5fd60b33f7 | ||
|
|
ec770aa724 | ||
|
|
8e7ecf2fc3 | ||
|
|
901f30ffd8 | ||
| b20852bcd4 | |||
|
|
08a75d6ed0 | ||
|
|
10aed47def | ||
|
|
1699da6b74 | ||
|
|
cd99c1fbc3 | ||
|
|
254431928f | ||
|
|
07aedcb866 | ||
|
|
fd341e332c | ||
|
|
5cf4df1fd8 | ||
|
|
34ba7e8271 | ||
|
|
60a7b790d4 | ||
|
|
4554fff534 | ||
|
|
86a0c50f6e | ||
|
|
3034020d56 | ||
| 6a66619c70 | |||
| 2ee7b3d2a2 | |||
| b7c0b1c8d4 | |||
| b8ebe03921 | |||
| 26635ace84 | |||
| 031be8ad5d | |||
| f316fabcb0 | |||
| b1dc8e0b5d | |||
| 641a479b6a | |||
| d80e15b55e | |||
|
|
1fcaf6e174 | ||
|
|
ef97bf0a75 | ||
|
|
4c8a8e43ed | ||
|
|
8db6992296 | ||
|
|
7925fc6caf | ||
|
|
b1f4ff2641 | ||
|
|
a852beff21 | ||
|
|
e17afe909f | ||
|
|
9ed37806dd | ||
|
|
5a21589029 | ||
|
|
189bce040b | ||
| e8c5b8a80c | |||
|
|
d47e3ed7f0 | ||
|
|
92ec16ce93 | ||
|
|
c2db65d9b1 | ||
|
|
1f008f1237 | ||
|
|
898cc8971b | ||
|
|
fd3c172e35 | ||
|
|
581863d69b |
52
.claude/skills/doc-drift-pipeline/SKILL.md
Normal file
@@ -0,0 +1,52 @@
|
||||
---
|
||||
name: doc-drift-pipeline
|
||||
description: Checks whether recent changes under tooling/pipeline/ have made docs/pipeline/ stale. Use when the user asks to check for doc drift on the pipeline, before committing changes to tooling/pipeline, or when asked "does this need a doc update" for the C++ seed-data pipeline.
|
||||
---
|
||||
|
||||
# Doc Drift Check — Pipeline
|
||||
|
||||
Given a diff scoped to `tooling/pipeline/` (uncommitted changes, a range of
|
||||
commits, or a specific PR), determine whether it invalidates any factual
|
||||
claim in `docs/pipeline/`.
|
||||
|
||||
## Steps
|
||||
|
||||
1. Run `git diff -- tooling/pipeline/` (or
|
||||
`git diff <base>...<head> -- tooling/pipeline/` if a range is given) to
|
||||
see what changed. If the diff also touches `web/**`, note that it's out of
|
||||
scope here — use the `doc-drift-web` skill for that half.
|
||||
2. Based on which files changed, identify the relevant doc(s):
|
||||
- `tooling/pipeline/src/**`, `includes/**` (implemented behavior) →
|
||||
`docs/pipeline/README.md`, `docs/pipeline/diagrams/current/*.mmd`
|
||||
(activity, class)
|
||||
- Work that's scaffolded/flagged but not wired into the default run path
|
||||
(roadmap-only) → `docs/pipeline/ROADMAP.md`,
|
||||
`docs/pipeline/diagrams/planned/*.mmd` — do not touch `current/` for
|
||||
planned work that hasn't landed
|
||||
- Changes to pipeline bias/hallucination handling, model prompts, sampling
|
||||
logic, or known-limitation workarounds →
|
||||
`docs/pipeline/ETHICS-AND-KNOWN-ISSUES.md`
|
||||
- `tooling/pipeline/runpod/Dockerfile`, build/run scripts →
|
||||
`docs/pipeline/README.md` (setup/usage sections)
|
||||
- `docs/pipeline/french-cities.example` — check it still matches the input
|
||||
schema the pipeline actually reads
|
||||
- A new file added under `docs/pipeline/**` → also check `docs/index.md`
|
||||
and `mkdocs.yml` nav are updated to reference it
|
||||
3. Read the relevant doc section(s) and check each specific factual claim
|
||||
(tables, "currently X", "not yet implemented", roadmap checkboxes) against
|
||||
the diff. For diagrams, this means reading the `.mmd` source (not just the
|
||||
wrapping `.md`) and checking nodes/edges/labels against the diff — a
|
||||
pipeline stage or control-flow change can invalidate a diagram without
|
||||
touching any prose.
|
||||
4. When a diff adds real behavior that was previously only in
|
||||
`diagrams/planned/`, check whether that planned diagram/roadmap entry
|
||||
should now move to `current/`/README rather than just adding a duplicate
|
||||
claim in both places.
|
||||
5. Report only what's actually stale — do not rewrite unrelated prose, do not
|
||||
invent claims not grounded in the diff.
|
||||
6. If nothing is affected, say so plainly and make no edits.
|
||||
7. For confirmed drift, propose the exact edit (old text → new text, or the
|
||||
changed `.mmd` node/edge) rather than committing directly, unless
|
||||
explicitly told to apply it. Flag `.mmd` changes separately since they may
|
||||
need a re-render (`docs/rendered-diagrams/pipeline/**`) via
|
||||
`docs/makefile`.
|
||||
55
.claude/skills/doc-drift-web/SKILL.md
Normal file
@@ -0,0 +1,55 @@
|
||||
---
|
||||
name: doc-drift-web
|
||||
description: Checks whether recent changes under web/ have made docs/web/ stale. Use when the user asks to check for doc drift on the web app, before committing changes to web/backend or web/frontend, or when asked "does this need a doc update" for web/API/frontend work.
|
||||
---
|
||||
|
||||
# Doc Drift Check — Web
|
||||
|
||||
Given a diff scoped to `web/` (uncommitted changes, a range of commits, or a
|
||||
specific PR), determine whether it invalidates any factual claim in
|
||||
`docs/web/`.
|
||||
|
||||
## Steps
|
||||
|
||||
1. Run `git diff -- web/` (or `git diff <base>...<head> -- web/` if a range is
|
||||
given) to see what changed. If the diff also touches `tooling/pipeline/**`,
|
||||
note that it's out of scope here — use the `doc-drift-pipeline` skill for
|
||||
that half.
|
||||
2. Based on which files changed, identify the relevant doc(s):
|
||||
- `web/backend/API/**`, `Features.*/**` (general) → `docs/web/architecture.md`
|
||||
- `web/backend/Features/Features.Users/**/Authentication/**`,
|
||||
identity/token code (`ITokenService`, `RefreshToken*`, `ConfirmEmail*`,
|
||||
login/registration handlers) → `docs/web/token-validation.md`,
|
||||
`docs/web/diagrams/auth/*.mmd` (pick the matching flow: login,
|
||||
registration, refresh-token, confirm-user, delete-account,
|
||||
update-email/password/profile/username, resend-confirmation,
|
||||
error-handling)
|
||||
- `web/backend/Database/**` (entities, `Database.Migrations/scripts/**`) →
|
||||
`docs/web/database.md`, `docs/web/diagrams/database-schema/*.mmd` (pick
|
||||
the matching schema: beer, brewery, identity, location, media)
|
||||
- Host wiring / DI registration (`API/**Program.cs`,
|
||||
`Database.Seed/**Program.cs`) → `docs/web/diagrams/vertical-slice/host-wiring.mmd`
|
||||
- New project references between `Features.*`/`Shared.*`/`Domain.*`
|
||||
projects (new `.csproj` `<ProjectReference>`) →
|
||||
`docs/web/diagrams/vertical-slice/project-references.mmd`
|
||||
- `web/backend/Dockerfile*`, `web/frontend/Dockerfile*`, compose/deploy
|
||||
config → `docs/web/docker.md`, `docs/web/diagrams/deployment/*.mmd`
|
||||
(dev, test, minimal, db-only, prod), `docs/web/diagrams/deployment.md`
|
||||
- `web/.env.example`, `web/.env.test`, appsettings → `docs/web/environment-variables.md`
|
||||
- `web/backend/API/API.Specs/**`, test infra/fixtures → `docs/web/testing.md`
|
||||
- New backend project setup, dev tooling → `docs/web/getting-started.md`
|
||||
- `web/frontend/**` → `docs/web/architecture.md` (Frontend architecture section)
|
||||
- A new file added under `docs/web/**` → also check `docs/index.md` and
|
||||
`mkdocs.yml` nav are updated to reference it
|
||||
3. Read the relevant doc section(s) and check each specific factual claim
|
||||
(tables, "currently X", "not yet implemented", roadmap checkboxes) against
|
||||
the diff. For diagrams, this means reading the `.mmd` source (not just the
|
||||
wrapping `.md`) and checking nodes/edges/labels against the diff — a
|
||||
schema or flow change can invalidate a diagram without touching any prose.
|
||||
4. Report only what's actually stale — do not rewrite unrelated prose, do not
|
||||
invent claims not grounded in the diff.
|
||||
5. If nothing is affected, say so plainly and make no edits.
|
||||
6. For confirmed drift, propose the exact edit (old text → new text, or the
|
||||
changed `.mmd` node/edge) rather than committing directly, unless
|
||||
explicitly told to apply it. Flag `.mmd` changes separately since they may
|
||||
need a re-render (`docs/rendered-diagrams/web/**`) via `docs/makefile`.
|
||||
@@ -1,13 +0,0 @@
|
||||
{
|
||||
"version": 1,
|
||||
"isRoot": true,
|
||||
"tools": {
|
||||
"csharpier": {
|
||||
"version": "1.2.1",
|
||||
"commands": [
|
||||
"csharpier"
|
||||
],
|
||||
"rollForward": false
|
||||
}
|
||||
}
|
||||
}
|
||||
1
.gitattributes
vendored
Normal file
@@ -0,0 +1 @@
|
||||
archive/** linguist-vendored
|
||||
20
.github/ISSUE_TEMPLATE/feature_request.md
vendored
@@ -7,6 +7,7 @@ assignees: []
|
||||
---
|
||||
|
||||
## User Story
|
||||
|
||||
**As a** (who wants to accomplish something)
|
||||
**I want to** (what they want to accomplish)
|
||||
**So that** (why they want to accomplish that thing)
|
||||
@@ -15,29 +16,18 @@ assignees: []
|
||||
|
||||
### Scenario 1
|
||||
|
||||
|
||||
Given ...
|
||||
When ...
|
||||
Then ...
|
||||
|
||||
Given ... When ... Then ...
|
||||
|
||||
### Scenario 2
|
||||
|
||||
|
||||
Given ...
|
||||
When ...
|
||||
Then ...
|
||||
|
||||
Given ... When ... Then ...
|
||||
|
||||
### Scenario 3
|
||||
|
||||
|
||||
Given ...
|
||||
When ...
|
||||
Then ...
|
||||
|
||||
Given ... When ... Then ...
|
||||
|
||||
## Subtasks
|
||||
|
||||
- [ ] Task 1
|
||||
- [ ] Task 2
|
||||
- [ ] Task 3
|
||||
101
.github/pull_request_template.md
vendored
Normal file
@@ -0,0 +1,101 @@
|
||||
## Summary
|
||||
|
||||
<!--
|
||||
State WHAT is changing and WHY, in two to five sentences.
|
||||
A reader should understand the change without opening the diff.
|
||||
Describe the problem first, then the outcome.
|
||||
-->
|
||||
|
||||
## Type of change
|
||||
|
||||
<!-- Tick the one option that best describes this PR. -->
|
||||
|
||||
- [ ] Bug fix
|
||||
- [ ] New feature
|
||||
- [ ] Refactor (no change in behaviour)
|
||||
- [ ] Performance improvement
|
||||
- [ ] Documentation
|
||||
- [ ] Tests only
|
||||
- [ ] Build, CI or dependency update
|
||||
- [ ] Other (please specify):
|
||||
|
||||
## Related issues
|
||||
|
||||
<!--
|
||||
Link the issue(s) this PR relates to. Use one keyword per issue so that each is closed on merge:
|
||||
|
||||
Fixes #123
|
||||
Fixes #124, fixes #125
|
||||
Fixes owner/other-repo#456
|
||||
|
||||
Closing keywords only take effect when the PR targets the repository's default branch.
|
||||
Use "Related to #123" if the PR should not close the issue.
|
||||
If there is no issue, write "N/A" and explain the motivation in the Summary.
|
||||
-->
|
||||
|
||||
## Approach and context
|
||||
|
||||
<!--
|
||||
Explain how the change works and why this approach was chosen.
|
||||
Include, where relevant:
|
||||
- The decisions you made that are not obvious from the code.
|
||||
- Alternatives you considered and why you rejected them.
|
||||
- Known limitations or shortcomings, and any planned follow-up work.
|
||||
- Background such as benchmark results or design documents.
|
||||
|
||||
Summarise the key points of any external link. Links may be inaccessible to future readers.
|
||||
-->
|
||||
|
||||
## How this was tested
|
||||
|
||||
<!--
|
||||
Describe what you ran and what you observed. Be specific, and state only what you actually did.
|
||||
For example: the automated tests added or changed, manual steps and their outcome,
|
||||
environments or platforms covered, and anything you were unable to test.
|
||||
For a bug fix, note the test that fails without the fix.
|
||||
-->
|
||||
|
||||
## Compatibility and risk
|
||||
|
||||
- [ ] This change is backwards compatible.
|
||||
- [ ] This change is **breaking** (complete the details below).
|
||||
- [ ] This change deprecates existing behaviour (complete the details below).
|
||||
|
||||
<!--
|
||||
If breaking or deprecating, describe: what changes, who is affected,
|
||||
and the migration path or recommended alternative.
|
||||
Also note any deployment, configuration, data migration or rollback considerations.
|
||||
-->
|
||||
|
||||
## User-facing change
|
||||
|
||||
<!--
|
||||
Does this PR change behaviour that users, operators or API consumers will notice?
|
||||
If not, write "None".
|
||||
If so, write one or two sentences suitable for release notes, in plain language and from the
|
||||
user's point of view. If users must take action when upgrading, state clearly that action is required.
|
||||
-->
|
||||
|
||||
```release-note
|
||||
|
||||
```
|
||||
|
||||
## Notes for reviewers
|
||||
|
||||
<!--
|
||||
Help reviewers focus. For example:
|
||||
- Where to start, or a suggested order in which to read the files.
|
||||
- Areas where you would particularly value scrutiny, or where you are uncertain.
|
||||
- How any mechanical, generated or bulk changes were produced (for example a search-and-replace
|
||||
or a code generator), so that reviewers can reproduce the steps.
|
||||
- Screenshots or recordings for visual changes (include before and after where useful).
|
||||
-->
|
||||
|
||||
## Checklist
|
||||
- [ ] The PR has a single, focused purpose and contains no unrelated changes.
|
||||
- [ ] The title is a clear, imperative summary of the change (for example, "Add retry to payment client").
|
||||
- [ ] I have added or updated tests that cover this change.
|
||||
- [ ] The build succeeds and the tests pass locally.
|
||||
- [ ] The code follows the existing patterns and style of this repository.
|
||||
- [ ] I have updated documentation, changelogs or API references where required.
|
||||
- [ ] I have reviewed my own diff, and this description reflects the final state of the change.
|
||||
51
.github/workflows/deploy-docs.yml
vendored
Normal file
@@ -0,0 +1,51 @@
|
||||
name: Deploy Docs to GitHub Pages
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
- docs
|
||||
paths:
|
||||
- "docs/**"
|
||||
- "mkdocs.yml"
|
||||
- ".github/workflows/deploy-docs.yml"
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
pages: write
|
||||
id-token: write
|
||||
|
||||
concurrency:
|
||||
group: pages
|
||||
cancel-in-progress: false
|
||||
|
||||
jobs:
|
||||
deploy:
|
||||
runs-on: ubuntu-latest
|
||||
environment:
|
||||
name: github-pages
|
||||
url: ${{ steps.deployment.outputs.page_url }}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Set up Python
|
||||
uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: "3.11"
|
||||
|
||||
- name: Install dependencies
|
||||
run: pip install mkdocs mkdocs-material mkdocs-glightbox mkdocs-panzoom-plugin mkdocs-minify-plugin
|
||||
|
||||
- name: Build site
|
||||
run: mkdocs build
|
||||
|
||||
- name: Upload artifact
|
||||
uses: actions/upload-pages-artifact@v3
|
||||
with:
|
||||
path: "site"
|
||||
|
||||
- name: Deploy to GitHub Pages
|
||||
id: deployment
|
||||
uses: actions/deploy-pages@v4
|
||||
61
.github/workflows/tests.yml
vendored
Normal file
@@ -0,0 +1,61 @@
|
||||
name: Tests
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
pull_request:
|
||||
branches: [main]
|
||||
|
||||
jobs:
|
||||
containerized-tests:
|
||||
runs-on: ubuntu-latest
|
||||
defaults:
|
||||
run:
|
||||
working-directory: web
|
||||
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v5
|
||||
|
||||
- name: Generate test environment file
|
||||
run: ./generate-env.sh .env.test
|
||||
|
||||
- name: Build test images
|
||||
run:
|
||||
docker compose --env-file .env.test -f docker-compose.test.yaml build
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
docker compose --env-file .env.test -f docker-compose.test.yaml up -d
|
||||
docker compose --env-file .env.test -f docker-compose.test.yaml wait api.specs unit.tests frontend.tests || true
|
||||
|
||||
- name: Check test container exit codes
|
||||
if: always()
|
||||
run: |
|
||||
status=0
|
||||
for name in test-env-database-migrations test-env-database-seed test-env-api-specs test-env-unit-tests test-env-frontend-tests; do
|
||||
code="$(docker inspect -f '{{.State.ExitCode}}' "$name" 2>/dev/null || echo 1)"
|
||||
echo "$name exited with $code"
|
||||
if [ "$code" != "0" ]; then
|
||||
status=1
|
||||
fi
|
||||
done
|
||||
exit $status
|
||||
|
||||
- name: Show service logs on failure
|
||||
if: failure()
|
||||
run:
|
||||
docker compose --env-file .env.test -f docker-compose.test.yaml logs
|
||||
|
||||
- name: Upload test results
|
||||
if: always()
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: test-results
|
||||
path: web/test-results
|
||||
|
||||
- name: Tear down
|
||||
if: always()
|
||||
run:
|
||||
docker compose --env-file .env.test -f docker-compose.test.yaml down
|
||||
-v
|
||||
18
.gitignore
vendored
@@ -1,5 +1,5 @@
|
||||
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
|
||||
|
||||
scratchpad.txt
|
||||
# dependencies
|
||||
/node_modules
|
||||
/.pnp
|
||||
@@ -16,12 +16,13 @@
|
||||
/build
|
||||
|
||||
# project-specific build artifacts
|
||||
/src/Website/build/
|
||||
/src/Website/storybook-static/
|
||||
/src/Website/.react-router/
|
||||
/src/Website/playwright-report/
|
||||
/src/Website/test-results/
|
||||
/web/frontend/build/
|
||||
/web/frontend/storybook-static/
|
||||
/web/frontend/.react-router/
|
||||
/web/frontend/playwright-report/
|
||||
/web/frontend/test-results/
|
||||
/test-results/
|
||||
/docs/rendered-diagrams/
|
||||
|
||||
# misc
|
||||
.DS_Store
|
||||
@@ -501,3 +502,8 @@ FodyWeavers.xsd
|
||||
|
||||
*storybook.log
|
||||
storybook-static
|
||||
web/test-results/frontend/vitest-storybook.xml
|
||||
web/test-results/frontend/playwright-storybook.xml
|
||||
|
||||
# mkdocs build output
|
||||
/site
|
||||
|
||||
962
LICENSE.md
203
README.md
@@ -1,159 +1,182 @@
|
||||
# The Biergarten App
|
||||
|
||||
The Biergarten App is a multi-project monorepo with a .NET backend and an active React
|
||||
Router frontend in `src/Website`. The current website focuses on account flows, theme
|
||||
switching, shared UI components, Storybook coverage, and integration with the API.
|
||||
The Biergarten App is a full-stack directory and discovery platform for
|
||||
breweries. It provides:
|
||||
|
||||
- JWT-based user authentication, with email confirmation and refresh-token
|
||||
reissue
|
||||
- A searchable database of brewery locations
|
||||
- An offline data-generation pipeline that uses large language models (LLMs)
|
||||
via Llama.cpp and Wikipedia to synthesize realistic seed data
|
||||
|
||||
The repository is organized into:
|
||||
|
||||
- A .NET backend (Web API + database migrations/seed) under `web/backend/`
|
||||
- A server-rendered React website (React Router + Vite) under `web/frontend/`
|
||||
- A C++20 data-generation CLI under `tooling/pipeline/`
|
||||
|
||||
Specialized documentation (setup, architecture, docker, testing, diagrams, and
|
||||
pipeline notes) lives under `docs/`.
|
||||
|
||||
## Documentation
|
||||
|
||||
- [Getting Started](docs/getting-started.md) - Local setup for backend and active website
|
||||
- [Architecture](docs/architecture.md) - Current backend and frontend architecture
|
||||
- [Docker Guide](docs/docker.md) - Container-based backend development and testing
|
||||
- [Testing](docs/testing.md) - Backend and frontend test commands
|
||||
- [Environment Variables](docs/environment-variables.md) - Active configuration reference
|
||||
- [Token Validation](docs/token-validation.md) - JWT validation architecture
|
||||
- [Legacy Website Archive](docs/archive/legacy-website-v1.md) - Archived notes for the old Next.js frontend
|
||||
Website + backend (active stack):
|
||||
|
||||
## Diagrams
|
||||
- [Getting Started](docs/web/getting-started.md)
|
||||
- [Architecture](docs/web/architecture.md)
|
||||
- [Database](docs/web/database.md)
|
||||
- [Docker Guide](docs/web/docker.md)
|
||||
- [Testing](docs/web/testing.md)
|
||||
- [Environment Variables](docs/web/environment-variables.md)
|
||||
- [Token Validation](docs/web/token-validation.md)
|
||||
|
||||
- [Architecture](docs/diagrams-out/architecture.svg) - Layered architecture
|
||||
- [Deployment](docs/diagrams-out/deployment.svg) - Docker topology
|
||||
- [Authentication Flow](docs/diagrams-out/authentication-flow.svg) - Auth sequence
|
||||
- [Database Schema](docs/diagrams-out/database-schema.svg) - Entity relationships
|
||||
Data generation pipeline (C++):
|
||||
|
||||
## Current Status
|
||||
- [Pipeline README](docs/pipeline/README.md)
|
||||
- [Ethics & Known Issues](docs/pipeline/ETHICS-AND-KNOWN-ISSUES.md)
|
||||
|
||||
## Current status
|
||||
|
||||
Active areas in the repository:
|
||||
|
||||
- .NET 10 backend with layered architecture and SQL Server
|
||||
- React Router 7 website in `src/Website`
|
||||
- Shared Biergarten theme system with a theme guide route
|
||||
- Storybook stories and browser-based checks for shared UI
|
||||
- Auth demo flows for home, login, register, dashboard, logout, and confirmation
|
||||
- Toast-based feedback for auth outcomes
|
||||
- .NET 10 backend (vertical-slice architecture with MediatR) + SQL Server
|
||||
- React 19 website (React Router 8 + Vite)
|
||||
- Shared Biergarten theme system + Storybook coverage
|
||||
- Auth flows and account/email integration (local Mailpit in dev compose)
|
||||
- Photo upload to S3-compatible object storage (local SeaweedFS in dev compose)
|
||||
- Data generation pipeline with C++ and Llama.cpp
|
||||
|
||||
Legacy area retained for reference:
|
||||
Archived/reference areas:
|
||||
|
||||
- `src/Website-v1` contains the archived Next.js frontend and is no longer the active website
|
||||
- `archive/next-js-web-app/` contains an older Next.js frontend retained for
|
||||
reference
|
||||
|
||||
## Tech Stack
|
||||
## Tech stack
|
||||
|
||||
- **Backend**: .NET 10, ASP.NET Core, SQL Server 2022, DbUp
|
||||
- **Frontend**: React 19, React Router 7, Vite 7, Tailwind CSS 4, DaisyUI 5
|
||||
- **Frontend**: React 19, React Router 8, Vite 7, Tailwind CSS 4, DaisyUI 5,
|
||||
Leaflet/React Leaflet (brewery maps)
|
||||
- **UI Documentation**: Storybook 10, Vitest browser mode, Playwright
|
||||
- **Testing**: xUnit, Reqnroll (BDD), FluentAssertions, Moq
|
||||
- **Infrastructure**: Docker, Docker Compose
|
||||
- **Security**: Argon2id password hashing, JWT access/refresh/confirmation tokens
|
||||
- **Security**: Argon2id password hashing, JSON Web Tokens (JWT) for
|
||||
access/refresh/confirmation
|
||||
- **Data Pipeline**: C++20, CMake, Boost, libcurl, SQLite, llama.cpp
|
||||
|
||||
## Quick Start
|
||||
## Requirements
|
||||
|
||||
### Backend
|
||||
- .NET SDK 10 or later
|
||||
- Node.js 22 or later
|
||||
- Docker Desktop, or an equivalent Docker Engine setup
|
||||
|
||||
See [Getting Started](docs/web/getting-started.md) for the full
|
||||
prerequisite list, including the pipeline's C++ toolchain.
|
||||
|
||||
## Quick start
|
||||
|
||||
For full setup details, use [Getting Started](docs/web/getting-started.md).
|
||||
This section is the shortest path to a working dev environment.
|
||||
|
||||
### Full stack (Docker)
|
||||
|
||||
```bash
|
||||
git clone https://github.com/aaronpo97/the-biergarten-app
|
||||
cd the-biergarten-app
|
||||
cp .env.example .env.dev
|
||||
docker compose -f docker-compose.dev.yaml up -d
|
||||
|
||||
cd web && ./generate-env.sh .env.dev && cd ..
|
||||
docker compose --env-file web/.env.dev -f web/docker-compose.dev.yaml up --build -d
|
||||
```
|
||||
|
||||
Backend access:
|
||||
`generate-env.sh` copies `.env.example` and replaces the secret-bearing values
|
||||
with freshly randomized ones; a plain `cp` leaves placeholder secrets in
|
||||
place. See [Environment Variables](docs/web/environment-variables.md#generating-an-env-file)
|
||||
for details.
|
||||
|
||||
Access:
|
||||
|
||||
- Website: http://localhost:3000
|
||||
- API Swagger: http://localhost:8080/swagger
|
||||
- Health Check: http://localhost:8080/health
|
||||
- Mailpit UI (dev SMTP): http://localhost:8025
|
||||
- SeaweedFS S3 API (dev object storage): http://localhost:8333
|
||||
|
||||
### Frontend
|
||||
### Frontend (Node, outside Docker)
|
||||
|
||||
```bash
|
||||
cd src/Website
|
||||
cd web/frontend
|
||||
npm install
|
||||
API_BASE_URL=http://localhost:8080 SESSION_SECRET=dev-secret npm run dev
|
||||
API_BASE_URL=http://localhost:8080 SESSION_SECRET=dev-secret-change-me npm run dev
|
||||
```
|
||||
|
||||
Optional frontend tools:
|
||||
|
||||
```bash
|
||||
cd src/Website
|
||||
cd web/frontend
|
||||
npm run storybook
|
||||
npm run test:storybook
|
||||
npm run test:storybook:playwright
|
||||
```
|
||||
|
||||
## Repository Structure
|
||||
## Repository structure
|
||||
|
||||
```text
|
||||
src/Core/ Backend projects (.NET)
|
||||
src/Website/ Active React Router frontend
|
||||
src/Website-v1/ Archived legacy Next.js frontend
|
||||
docs/ Active project documentation
|
||||
docs/archive/ Archived legacy documentation
|
||||
web/
|
||||
backend/ .NET API: API.Core (host), Features.* (vertical slices),
|
||||
Shared.*, Domain.*, Infrastructure.*, Database.* projects
|
||||
frontend/ React Router website + Storybook + Playwright/Vitest
|
||||
|
||||
tooling/
|
||||
pipeline/ C++20 seed-data generation CLI (CMake)
|
||||
|
||||
docs/
|
||||
web/ Architecture, setup, docker, testing, diagrams
|
||||
pipeline/ Pipeline docs, ethics notes, diagrams
|
||||
|
||||
archive/
|
||||
next-js-web-app/ Older Next.js frontend (reference only)
|
||||
```
|
||||
|
||||
## Key Features
|
||||
|
||||
Implemented today:
|
||||
|
||||
- User registration and login against the API
|
||||
- JWT-based auth with access, refresh, and confirmation flows
|
||||
- SQL Server migrations and seed projects
|
||||
- Shared form components and auth screens
|
||||
- Theme switching with Lager, Stout, Cassis, and Weizen variants
|
||||
- Storybook documentation and automated story interaction tests
|
||||
- Toast feedback for auth-related outcomes
|
||||
|
||||
Planned next:
|
||||
|
||||
- Brewery discovery and management
|
||||
- Beer reviews and ratings
|
||||
- Social follow relationships
|
||||
- Geospatial brewery experiences
|
||||
- Additional frontend routes beyond the auth demo
|
||||
|
||||
## Testing
|
||||
|
||||
Backend suites:
|
||||
|
||||
- `API.Specs` - integration tests
|
||||
- `Infrastructure.Repository.Tests` - repository unit tests
|
||||
- `Service.Auth.Tests` - service unit tests
|
||||
|
||||
Frontend suites:
|
||||
|
||||
- Storybook interaction tests via Vitest
|
||||
- Storybook browser regression checks via Playwright
|
||||
|
||||
Run all backend tests with Docker:
|
||||
Create a test environment file, then run the full test stack (backend and
|
||||
frontend) with Docker:
|
||||
|
||||
```bash
|
||||
docker compose -f docker-compose.test.yaml up --abort-on-container-exit
|
||||
cd web && ./generate-env.sh .env.test && cd ..
|
||||
docker compose --env-file web/.env.test -f web/docker-compose.test.yaml up --abort-on-container-exit
|
||||
```
|
||||
|
||||
See [Testing](docs/testing.md) for the full command list.
|
||||
The same command runs in CI via
|
||||
[`.github/workflows/tests.yml`](.github/workflows/tests.yml) on every push
|
||||
and pull request to `main`. See [Testing](docs/web/testing.md) for the
|
||||
full command list.
|
||||
|
||||
## Configuration
|
||||
|
||||
Common active variables:
|
||||
|
||||
- Backend: `DB_SERVER`, `DB_NAME`, `DB_USER`, `DB_PASSWORD`, `ACCESS_TOKEN_SECRET`, `REFRESH_TOKEN_SECRET`, `CONFIRMATION_TOKEN_SECRET`
|
||||
- Frontend: `API_BASE_URL`, `SESSION_SECRET`, `NODE_ENV`
|
||||
- Backend/Docker: `DB_SERVER`, `DB_NAME`, `DB_USER`, `DB_PASSWORD`,
|
||||
`ACCESS_TOKEN_SECRET`, `REFRESH_TOKEN_SECRET`, `CONFIRMATION_TOKEN_SECRET`,
|
||||
`WEBSITE_BASE_URL`
|
||||
- Frontend runtime: `API_BASE_URL`, `SESSION_SECRET`, `NODE_ENV`
|
||||
|
||||
See [Environment Variables](docs/environment-variables.md) for details.
|
||||
See [Environment Variables](docs/web/environment-variables.md) for details.
|
||||
|
||||
## Contributing
|
||||
|
||||
1. Fork the repository
|
||||
2. Create a feature branch (`git checkout -b feature/amazing-feature`)
|
||||
3. Commit your changes (`git commit -m 'Add amazing feature'`)
|
||||
4. Push to the branch (`git push origin feature/amazing-feature`)
|
||||
5. Open a Pull Request
|
||||
|
||||
### Development Workflow
|
||||
|
||||
1. Start development environment: `docker compose -f docker-compose.dev.yaml up -d`
|
||||
2. Make changes to code
|
||||
3. Run tests: `docker compose -f docker-compose.test.yaml up --abort-on-container-exit`
|
||||
4. Rebuild if needed: `docker compose -f docker-compose.dev.yaml up -d --build api.core`
|
||||
4. Run the checks in [Testing](docs/web/testing.md) (backend tests,
|
||||
`npm run lint`, `npm run typecheck`)
|
||||
5. Push to the branch (`git push origin feature/amazing-feature`)
|
||||
6. Open a Pull Request
|
||||
|
||||
## Support
|
||||
|
||||
- **Documentation**: [docs/](docs/)
|
||||
- **Architecture**: See [Architecture Guide](docs/architecture.md)
|
||||
Report bugs and request features via
|
||||
[GitHub Issues](https://github.com/aaronpo97/the-biergarten-app/issues).
|
||||
|
||||
## License
|
||||
|
||||
GPL-3.0. See [LICENSE.md](LICENSE.md).
|
||||
|
||||
0
src/Website-v1/package-lock.json → archive/next-js-web-app/package-lock.json
generated
vendored
|
Before Width: | Height: | Size: 203 KiB After Width: | Height: | Size: 203 KiB |
|
Before Width: | Height: | Size: 7.3 KiB After Width: | Height: | Size: 7.3 KiB |
|
Before Width: | Height: | Size: 26 KiB After Width: | Height: | Size: 26 KiB |
|
Before Width: | Height: | Size: 6.5 KiB After Width: | Height: | Size: 6.5 KiB |
|
Before Width: | Height: | Size: 515 B After Width: | Height: | Size: 515 B |
|
Before Width: | Height: | Size: 961 B After Width: | Height: | Size: 961 B |
|
Before Width: | Height: | Size: 15 KiB After Width: | Height: | Size: 15 KiB |
|
Before Width: | Height: | Size: 256 KiB After Width: | Height: | Size: 256 KiB |