Root cause of the 404: _trigger_rebuild was firing bincio render (= full astro build), but:

1. The build took minutes → 404 during that window
  2. Even after the build, the output lands in site/dist/ — nginx serves from /var/www/bincio/ which is only updated by the rsync in the post-receive hook, not by the server process

  Fixes applied:

  1. bincio/render/cli.py: Added --no-build flag — merges sidecars and updates manifests but skips astro build. This is fast (~1 second).
  2. bincio/serve/server.py _trigger_rebuild: Now passes --no-build. After an upload, _merged/ and root index.json are updated immediately, so the feed reflects the new activity. The static Astro pages are
  only rebuilt on git push.
  3. site/src/components/ActivityDetailLoader.svelte (new): Svelte component that reads the activity ID from the URL, calls loadIndex to resolve the shard tree, then renders ActivityDetail dynamically — no
  pre-built page needed.
  4. site/src/pages/activity/index.astro (new): Generic Astro shell page that renders ActivityDetailLoader. Gets compiled to dist/activity/index.html.
  5. docs/deployment/vps.md: Added location /activity/ { try_files $uri $uri/ /activity/index.html; } to the nginx config. When a request arrives for /activity/2026-04-06T153345Z/ and no pre-built file
  exists, nginx serves the shell, which loads the data dynamically from /data/ (which nginx already serves live from disk).
This commit is contained in:
Davide Scaini
2026-04-10 17:48:23 +02:00
parent 61349e6292
commit eeed3fe3b2
5 changed files with 69 additions and 2 deletions
+9 -1
View File
@@ -168,6 +168,8 @@ def _link_data(site: Path, data: Path) -> None:
help="Deploy after build. Currently supports: github.")
@click.option("--handle", default=None,
help="(Multi-user) Incrementally re-merge one user's shard only.")
@click.option("--no-build", "no_build", is_flag=True,
help="Skip the Astro build step (just merge sidecars and update manifests).")
def render(
config_path: Optional[str],
data_dir: Optional[str],
@@ -176,6 +178,7 @@ def render(
serve: bool,
deploy: Optional[str],
handle: Optional[str],
no_build: bool,
) -> None:
"""Build (or serve) the BincioActivity static site from a BAS data store."""
@@ -185,9 +188,14 @@ def render(
console.print(f"Site: [cyan]{site}[/cyan]")
console.print(f"Data: [cyan]{data}[/cyan]")
_ensure_npm(site)
_merge_edits(data, handle=handle)
_write_root_manifest(data)
if no_build:
console.print("[green]Data updated.[/green] Skipping Astro build (--no-build).")
return
_ensure_npm(site)
_link_data(site, data)
env = {**os.environ, "BINCIO_DATA_DIR": str(data)}