Anson's Projects #
Source for projects.ansonbiggs.com, a Quarto technical blog that cross-posts rendered articles to notes.ansonbiggs.com.
Development environment #
Open the repository in its VS Code devcontainer. The pinned image includes Quarto, Julia, Python/Jupyter, R, Rust, Node, Pi, and Bun, and runs as the non-root vscode user.
The multi-stage Dockerfile exposes a smaller site target for CI rendering and a development target with Node/Pi/Bun/Rust for the devcontainer. A checked-in Manifest.toml and pinned tool versions keep both environments consistent.
Python authoring dependencies are declared in requirements.in and fully locked with hashes in requirements.txt. Regenerate the lock with:
uv pip compile requirements.in --python-version 3.11 --universal --generate-hashes --output-file requirements.txt
Render locally #
quarto render --to html --output-dir public
quarto render --profile ghost --to html --output-dir public/ghost-content
The public configuration is _quarto.yml. _quarto-ghost.yml is an overlay that produces minimal HTML for the Ghost transformer.
Validate changes #
Run the complete local workflow with:
make check
Or run individual checks:
bun test ./.pi/qmd-agents-tests/qmd-agents.test.ts
(cd ghost-upload && cargo test --locked)
(cd ghost-upload && cargo run --locked -- --dry-run)
The dry run reads public/index.xml and public/ghost-content, transforms every entry, and never accesses or mutates Ghost. Render both outputs first.
Agent-generated QMD fragments #
Type piagent in a QMD file in VS Code, or write:
<!-- pi-agent:include id="commute-plot" file="_agent/commute-plot.qmd"
Build and verify the requested section, including its data, code, and plot.
-->
{{< include _agent/commute-plot.qmd >}}
When Pi is open in this repository, .pi/extensions/qmd-agents.ts watches authored QMD files and prompts the agent after relevant saves. The agent writes the separate _agent/*.qmd fragment rather than the surrounding article. Commit generated fragments and supporting resources so CI remains deterministic and does not require an AI provider.
See .pi/extensions/qmd-agents.md for commands and safety details.
Publishing #
GitLab CI builds and tests both render variants on branches and merge requests. Only the default branch deploys Pages and runs the Ghost publisher. Production synchronization requires the protected GHOST_TOKEN CI variable.
Before an intentional manual publish:
(cd ghost-upload && cargo run --release --locked)
Changes affecting site rendering or Ghost transformation must be checked on the live Ghost post with Playwright after synchronization.