unaltraweb 0.5.0 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Makefile +18 -11
- data/README.md +4 -4
- data/_plugins/retained_documents.rb +62 -0
- data/docs/_documentation/en/02-tools.md +3 -3
- data/docs/_documentation/en/32-development.md +1 -1
- data/docs/_documentation/en/40-distribution.md +157 -12
- data/docs/_documentation/en/42-docker-image.md +7 -7
- data/docs/_documentation/en/45-retained-documents.md +138 -0
- data/docs/agents/mcp-contract.md +64 -2
- data/docs/agents/owner-closeout-76.md +205 -0
- data/docs/agents/owner-followup-76.md +144 -0
- data/docs/agents/owner-preparation-2026-09-29.md +254 -0
- data/docs/agents/retained-letter-import.md +231 -0
- data/docs/agents/visual-companions-0.4.0.md +5 -0
- data/lib/unaltraweb.rb +1 -0
- data/requirements.txt +2 -0
- data/scripts/manual/Dockerfile +7 -4
- data/scripts/manual/build_pdf.py +28 -0
- data/scripts/manual/templates/manual.tex +1 -0
- data/scripts/test_gem_build.py +28 -1
- data/scripts/test_wheel_install.py +51 -0
- data/scripts/unaltraweb-mcp-bootstrap.sh +33 -6
- data/scripts/validate_distribution.py +21 -2
- data/src/unaltraweb_mcp/__init__.py +4 -0
- data/src/unaltraweb_mcp/artifact-handoff-v1.schema.json +102 -0
- data/src/unaltraweb_mcp/artifact_handoff_v1.py +435 -0
- data/src/unaltraweb_mcp/artifact_imports.py +368 -0
- data/src/unaltraweb_mcp/bundler_runtime.py +214 -0
- data/src/unaltraweb_mcp/component-contract.json +20 -20
- data/src/unaltraweb_mcp/distribution.py +887 -0
- data/src/unaltraweb_mcp/letter_bundle.py +223 -0
- data/src/unaltraweb_mcp/pdf_probe.py +63 -0
- metadata +16 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 33193d7900939e3cf2e4e9769e8fd9443e0a7242eaa73aef1d93b8ffcee6e79b
|
|
4
|
+
data.tar.gz: 3ef63e4f55c4b369e0926be413eb2da4d3702f49ac733d84dedc952bb1ec563c
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: eb799646f841a4444d315aa4a71d161ec83acacbef75f36fe00b8db7242699be40147c2829bedee18f249f3085b51328cd18a902f317196d518b4f2b8e11a9f2
|
|
7
|
+
data.tar.gz: cfe5a103146718d7bbae56c9821b2dabdc0fdf1bcde966779ee41ea96c468bd795446202844a56a0974919ce4bca33e2d90e5c6de98e8e95936b1335c44dca86
|
data/Makefile
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
PYTHON ?= python3
|
|
2
2
|
override PROJECT := $${MCP_CONSUMER_WORKSPACE:?MCP_CONSUMER_WORKSPACE is required}
|
|
3
3
|
override PROJECT_ROOT := $(PROJECT)
|
|
4
|
-
MCP_RUNTIME_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb:0.
|
|
5
|
-
MCP_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.
|
|
6
|
-
MCP_RELEASE_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb-mcp@sha256:
|
|
4
|
+
MCP_RUNTIME_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb:0.6.0
|
|
5
|
+
MCP_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.6.0
|
|
6
|
+
MCP_RELEASE_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb-mcp@sha256:908b4ce54c7bdf355e14ed55b31ed4b9baae319e211af90004a680d1d1cb8692
|
|
7
7
|
MCP_DOCKER_BUILD_NETWORK ?= default
|
|
8
8
|
INIT_SITE_PROFILE ?= unaltreselfie
|
|
9
9
|
NEW_WEB_PROFILE ?= unaltreselfie
|
|
@@ -40,10 +40,13 @@ WEB_CAPTURE_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb-web-capture@sha256:0bf1b
|
|
|
40
40
|
WEB_CAPTURE_DEV_IMAGE ?= unaltraweb-web-capture:dev
|
|
41
41
|
WEB_CAPTURE_DOCKER_BUILD_NETWORK ?= default
|
|
42
42
|
VEGAVISUALS_CLI ?=
|
|
43
|
-
DOCKER_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb:0.
|
|
44
|
-
MANUAL_PDF_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb-manual-pdf@sha256:
|
|
43
|
+
DOCKER_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb:0.6.0
|
|
44
|
+
MANUAL_PDF_IMAGE ?= ghcr.io/dosquartsdedocs/unaltraweb-manual-pdf@sha256:0ba267cb87f53ebaca4e31805fe00610cd61fdf97a8d2c3692f4655700dceaed
|
|
45
45
|
MANUAL_PDF_DEV_IMAGE ?= unaltraweb-manual-pdf:dev
|
|
46
46
|
MCP_SMOKE_MANUAL_PDF_IMAGE ?= $(MANUAL_PDF_IMAGE)
|
|
47
|
+
MCP_SMOKE_PROJECT ?=
|
|
48
|
+
override MCP_SMOKE_PROJECT := $(value MCP_SMOKE_PROJECT)
|
|
49
|
+
export MCP_SMOKE_PROJECT
|
|
47
50
|
MANUAL_PDF_LANG ?=
|
|
48
51
|
MANUAL_PDF_PUBLISH_DRY_RUN ?= 1
|
|
49
52
|
MANUAL_PDF_CONFIRM_PUBLISH ?= 0
|
|
@@ -142,14 +145,18 @@ mcp-smoke: mcp-image manual-pdf-image-dev ## Build and prove a real MCP stdio co
|
|
|
142
145
|
|
|
143
146
|
mcp-smoke-prebuilt: ## Prove a real MCP stdio connection using the selected prebuilt MCP image
|
|
144
147
|
docker run --rm --user "$(LOCAL_UID):$(LOCAL_GID)" -e HOME=/tmp --entrypoint python3 "$(MCP_IMAGE)" /opt/unaltraweb/test/mcp_smoke.py
|
|
145
|
-
@mkdir -p "$(CURDIR)/tmp
|
|
146
|
-
@
|
|
148
|
+
@mkdir -p "$(CURDIR)/tmp"
|
|
149
|
+
@project="$${MCP_SMOKE_PROJECT:-}"; \
|
|
150
|
+
if test -n "$$project"; then mkdir -- "$$project" || exit $$?; \
|
|
151
|
+
else project=$$(mktemp -d "$(CURDIR)/tmp/mcp-preview-smoke.XXXXXX") || exit $$?; fi; \
|
|
152
|
+
project=$$(realpath -e -- "$$project") || exit $$?; \
|
|
153
|
+
docker_socket="$${UNALTRAWEB_DOCKER_SOCKET:-/var/run/docker.sock}"; socket_group=$$(stat -c '%g' "$$docker_socket"); \
|
|
147
154
|
image_id=$$(docker image inspect --format '{{.Id}}' "$(MCP_IMAGE)"); \
|
|
148
155
|
socket_mount=$$(/bin/sh "$(DOCKER_MOUNT_SCRIPT)" "$$docker_socket" /var/run/docker.sock); \
|
|
149
|
-
project_mount=$$(/bin/sh "$(DOCKER_MOUNT_SCRIPT)" "
|
|
150
|
-
mirror_mount=$$(/bin/sh "$(DOCKER_MOUNT_SCRIPT)" "
|
|
156
|
+
project_mount=$$(/bin/sh "$(DOCKER_MOUNT_SCRIPT)" "$$project" /workspace); \
|
|
157
|
+
mirror_mount=$$(/bin/sh "$(DOCKER_MOUNT_SCRIPT)" "$$project" "$$project"); \
|
|
151
158
|
docker run --rm --user "$(LOCAL_UID):$(LOCAL_GID)" --group-add "$$socket_group" \
|
|
152
|
-
-e HOME=/tmp -e "UNALTRAWEB_DOCKER_ROOT
|
|
159
|
+
-e HOME=/tmp -e "UNALTRAWEB_DOCKER_ROOT=$$project" \
|
|
153
160
|
-e "UNALTRAWEB_PROJECT_USER=$(LOCAL_UID):$(LOCAL_GID)" -e "UNALTRAWEB_MCP_IMAGE=$$image_id" \
|
|
154
161
|
-e "MANUAL_PDF_IMAGE=$(MCP_SMOKE_MANUAL_PDF_IMAGE)" \
|
|
155
162
|
--mount "$$socket_mount" \
|
|
@@ -368,7 +375,7 @@ manual-pdf-image: ## Ensure the selected versioned Pandoc/XeLaTeX image is prese
|
|
|
368
375
|
@docker image inspect "$(MANUAL_PDF_IMAGE)" >/dev/null 2>&1 || docker pull "$(MANUAL_PDF_IMAGE)"
|
|
369
376
|
|
|
370
377
|
manual-pdf-image-dev: ## Build the explicitly named maintainer PDF development image
|
|
371
|
-
docker build -f scripts/manual/Dockerfile -t "$(MANUAL_PDF_DEV_IMAGE)"
|
|
378
|
+
docker build -f scripts/manual/Dockerfile -t "$(MANUAL_PDF_DEV_IMAGE)" .
|
|
372
379
|
|
|
373
380
|
define run_manual_pdf_worker
|
|
374
381
|
@set -e; set --; cidfile=""; \
|
data/README.md
CHANGED
|
@@ -34,7 +34,7 @@ The default distribution is Docker-first. Generated sites run their normal build
|
|
|
34
34
|
|
|
35
35
|
## Current Status
|
|
36
36
|
|
|
37
|
-
- Public release `v0.
|
|
37
|
+
- Public release [`v0.5.0`](https://github.com/dosquartsdedocs/unaltraweb/releases/tag/v0.5.0) provides the Docker images, Ruby gem and Python wheel as one receipt-bound distribution.
|
|
38
38
|
- `ghcr.io/dosquartsdedocs/unaltraweb-mcp` is the canonical normal local runtime for generated sites; `ghcr.io/dosquartsdedocs/unaltraweb` is its lower-level Jekyll runtime base.
|
|
39
39
|
- The Ruby gem supports native Bundler/Jekyll consumers. The modular MCP wheel supports native creation and inspection, and does not bundle the gem, factory checkout, worker images or companion renderers.
|
|
40
40
|
- PDF, browser-capture and computation environments remain separate images so the normal site image does not carry every heavy toolchain.
|
|
@@ -74,11 +74,11 @@ Create a child site directly with the public Docker image:
|
|
|
74
74
|
mkdir my-site && \
|
|
75
75
|
docker run --rm --network none --user "$(id -u):$(id -g)" -e HOME=/tmp \
|
|
76
76
|
--mount "type=bind,src=${PWD}/my-site,dst=/workspace" \
|
|
77
|
-
ghcr.io/dosquartsdedocs/unaltraweb-mcp@sha256:
|
|
77
|
+
ghcr.io/dosquartsdedocs/unaltraweb-mcp@sha256:36d17edbade77edb40a687f6a744203c6329acb33fbc2eb255e88d9ff1a42c98 \
|
|
78
78
|
--project /workspace new-web --site-profile unaltreselfie --title "My site" --default-lang en
|
|
79
79
|
```
|
|
80
80
|
|
|
81
|
-
The chained `mkdir` requires a new destination, the digest binds creation to the reviewed `v0.
|
|
81
|
+
The chained `mkdir` requires a new destination, the digest binds creation to the reviewed `v0.5.0` receipt, and `--network none` keeps scaffold generation offline.
|
|
82
82
|
|
|
83
83
|
If Python package tooling is already available, the PyPI adapter exposes the equivalent native command:
|
|
84
84
|
|
|
@@ -129,7 +129,7 @@ make docs-serve DOCKER_IMAGE=unaltraweb:dev
|
|
|
129
129
|
make docs-build DOCKER_IMAGE=unaltraweb:dev
|
|
130
130
|
```
|
|
131
131
|
|
|
132
|
-
The public distribution contract selects `ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.
|
|
132
|
+
The public distribution contract selects `ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.5.0` for normal generated-site commands. `MCP_RELEASE_IMAGE` pins the reviewed MCP digest from the same `v0.5.0` receipt for gContExt (formerly ContExt), the GNOME Shell extension. The mutable `:main` channel is reserved for explicit maintainer testing; locally built core images use the `:dev` name.
|
|
133
133
|
|
|
134
134
|
The lower-level `unaltraweb` image supplies Ruby, Jekyll and runtime dependencies. The MCP image layers the full reviewed factory and installed Python package on top; generated Make targets load the theme as a path gem from `/opt/unaltraweb`. Native Bundler consumers can instead resolve the independently published gem, and native Python users can install the wheel.
|
|
135
135
|
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "cgi"
|
|
4
|
+
require "json"
|
|
5
|
+
require "open3"
|
|
6
|
+
require "timeout"
|
|
7
|
+
|
|
8
|
+
module UnaltrawebRetainedDocuments
|
|
9
|
+
def self.verify(site, output = nil)
|
|
10
|
+
return { "imports" => [] } unless File.exist?(File.join(site.source, ".unaltraweb", "artifacts"))
|
|
11
|
+
|
|
12
|
+
source = File.expand_path("../src", __dir__)
|
|
13
|
+
command = ["python3", "-m", "unaltraweb_mcp.artifact_imports", "--project", File.expand_path(site.source)]
|
|
14
|
+
command += ["--output-folder", output] if output
|
|
15
|
+
stdout, stderr, status = Timeout.timeout(120) { Open3.capture3({ "PYTHONPATH" => source }, *command) }
|
|
16
|
+
result = JSON.parse(stdout)
|
|
17
|
+
raise Jekyll::Errors::FatalException, "Retained document check failed: #{result['error'] || stderr}" unless status.success? && result["ok"] == true
|
|
18
|
+
|
|
19
|
+
result
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
class Generator < Jekyll::Generator
|
|
23
|
+
safe true
|
|
24
|
+
priority :highest
|
|
25
|
+
|
|
26
|
+
def generate(site)
|
|
27
|
+
site.config["unaltraweb_retained_documents"] = UnaltrawebRetainedDocuments.verify(site)["imports"].to_h { |item| [item["id"], item] }
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
class DocumentTag < Liquid::Tag
|
|
32
|
+
def initialize(name, markup, tokens)
|
|
33
|
+
super
|
|
34
|
+
@id = markup.strip
|
|
35
|
+
raise ArgumentError, "retained_document requires one import ID" unless @id.match?(/\A[a-z][a-z0-9-]{0,63}\z/)
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
def render(context)
|
|
39
|
+
site = context.registers[:site]
|
|
40
|
+
item = (site.config["unaltraweb_retained_documents"] || {})[@id]
|
|
41
|
+
raise Jekyll::Errors::FatalException, "Unverified retained document #{@id}" unless item
|
|
42
|
+
|
|
43
|
+
path = site.config["baseurl"].to_s.sub(%r{/\z}, "") + "/" + item.fetch("pdf")
|
|
44
|
+
url = CGI.escapeHTML(path)
|
|
45
|
+
page = context["page"]
|
|
46
|
+
title = CGI.escapeHTML(((page && page["title"]) || @id).to_s)
|
|
47
|
+
%(<figure class="retained-document"><object data-retained-document="#{@id}" data="#{url}" type="application/pdf" aria-label="#{title}" style="width:100%;height:70vh"><a href="#{url}">#{title}</a></object><figcaption><a href="#{url}">#{title} (PDF)</a></figcaption></figure>)
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
Liquid::Template.register_tag("retained_document", UnaltrawebRetainedDocuments::DocumentTag)
|
|
53
|
+
|
|
54
|
+
Jekyll::Hooks.register :site, :post_write do |site|
|
|
55
|
+
source = File.expand_path(site.source)
|
|
56
|
+
destination = File.expand_path(site.dest)
|
|
57
|
+
if destination.start_with?(source + "/")
|
|
58
|
+
UnaltrawebRetainedDocuments.verify(site, destination.delete_prefix(source + "/"))
|
|
59
|
+
elsif !(site.config["unaltraweb_retained_documents"] || {}).empty?
|
|
60
|
+
raise Jekyll::Errors::FatalException, "Retained documents require a project-confined site destination"
|
|
61
|
+
end
|
|
62
|
+
end
|
|
@@ -30,10 +30,10 @@ nav_title: Local Tools
|
|
|
30
30
|
The current public core runtime image is:
|
|
31
31
|
|
|
32
32
|
```bash
|
|
33
|
-
ghcr.io/dosquartsdedocs/unaltraweb:0.
|
|
33
|
+
ghcr.io/dosquartsdedocs/unaltraweb:0.5.0
|
|
34
34
|
```
|
|
35
35
|
|
|
36
|
-
That image provides Ruby, Bundler, Jekyll system dependencies, ImageMagick, Node for ExecJS and Python tooling needed by local commands. Package-generated `v0.
|
|
36
|
+
That image provides Ruby, Bundler, Jekyll system dependencies, ImageMagick, Node for ExecJS and Python tooling needed by local commands. Package-generated `v0.5.0` sites select the matching public MCP image for normal local commands. The external integration fixture can advance from its older release pin independently.
|
|
37
37
|
|
|
38
38
|
## Generated Site Commands
|
|
39
39
|
|
|
@@ -143,4 +143,4 @@ When the core docs and all template profiles are running together, use this conv
|
|
|
143
143
|
- Keep deploy workflows as thin `workflow_dispatch` wrappers pinned to a reviewed full commit SHA of `dosquartsdedocs/unaltraweb/.github/workflows/site-deploy.yml`.
|
|
144
144
|
- The optional integration template may retain its local `gh-pages` publishing target for testing that separate workflow.
|
|
145
145
|
- After the first Docker publish, make `ghcr.io/dosquartsdedocs/unaltraweb` public.
|
|
146
|
-
- Confirm `docker pull ghcr.io/dosquartsdedocs/unaltraweb:0.
|
|
146
|
+
- Confirm `docker pull ghcr.io/dosquartsdedocs/unaltraweb:0.5.0` works without `docker login`.
|
|
@@ -65,7 +65,7 @@ docker compose -f docker-compose.yml down --remove-orphans
|
|
|
65
65
|
|
|
66
66
|
This can be resource-heavy because the inherited demo build minifies JavaScript and can generate many responsive WebP images.
|
|
67
67
|
|
|
68
|
-
The currently public base Dockerfile image is `ghcr.io/dosquartsdedocs/unaltraweb:0.
|
|
68
|
+
The currently public base Dockerfile image is `ghcr.io/dosquartsdedocs/unaltraweb:0.5.0`. Published generated consumers select the higher-level `ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.5.0`, which adds the reviewed core and Python control plane. Their Make targets use `/opt/unaltraweb` as a path gem; the RubyGems package remains the optional native Bundler channel. gContExt prepares the full post-release `MCP_RELEASE_IMAGE` digest with `mcp-build`, while `mcp-image`, `mcp-check` and `mcp-smoke` reserve local `:dev` names for source testing. Mutable `:main` channels remain explicit maintainer paths.
|
|
69
69
|
|
|
70
70
|
The root core build excludes `docs/`. The reference site is published from the `docs/` folder through a dedicated workflow so its root-relative permalinks do not collide with the inherited core demo build.
|
|
71
71
|
|
|
@@ -25,12 +25,52 @@ The template is the better place to validate gem consumption, centralized styles
|
|
|
25
25
|
|
|
26
26
|
## Component Contract
|
|
27
27
|
|
|
28
|
-
### 0.
|
|
29
|
-
|
|
30
|
-
The
|
|
28
|
+
### Pending 0.6.0 retained-letter increment
|
|
29
|
+
|
|
30
|
+
The source branch prepares a separate 0.6.0 identity for native
|
|
31
|
+
[retained-letter import]({{ '/retained-documents/' | relative_url }}).
|
|
32
|
+
Gem, wheel, base runtime and MCP are authorized as `ready` for final same-source
|
|
33
|
+
candidates. The consumer core selects reviewed integration
|
|
34
|
+
`5cf9817489c8dc47cee726bfe42fe3071cd32b85`; the PDF 0.6.0 worker is already
|
|
35
|
+
published, signed and tested at immutable digest
|
|
36
|
+
`sha256:0ba267cb87f53ebaca4e31805fe00610cd61fdf97a8d2c3692f4655700dceaed`.
|
|
37
|
+
The PDF worker changes to include complete retained documents and the same
|
|
38
|
+
integrity checkers used by its controller. Computation, capture and visual
|
|
39
|
+
companions retain their tested 0.4.0 selections.
|
|
40
|
+
|
|
41
|
+
The checkout's active launcher remains pinned to the published 0.5.1 MCP digest.
|
|
42
|
+
Its receipt and package bytes remain unchanged. Local development images and an
|
|
43
|
+
installed wheel exercise the new import without claiming a public 0.6.0 release
|
|
44
|
+
or changing real consumer sites. The
|
|
45
|
+
[owner acceptance record](https://github.com/dosquartsdedocs/unaltraweb/blob/main/docs/agents/retained-letter-import.md)
|
|
46
|
+
records the authenticated Carta packet, receiver mapping and relocation proof.
|
|
47
|
+
|
|
48
|
+
### Published 0.5.1 release
|
|
49
|
+
|
|
50
|
+
[**0.5.1**](https://github.com/dosquartsdedocs/unaltraweb/releases/tag/v0.5.1)
|
|
51
|
+
delivers the installed Docker launcher and runtime-specific generated Bundler
|
|
52
|
+
state. Source `aab5a7b030cd711b40770a3f44ad3a356eab90da` produced the signed
|
|
53
|
+
images and verified gem/wheel. Receipt/tag commit
|
|
54
|
+
`e842c733c8a274279dd5efdc3618e20669f29037` changes only the receipt from that
|
|
55
|
+
first parent. Strict release/publication gates passed before promotion, and
|
|
56
|
+
anonymous registry downloads match the receipt. The checkout launcher now selects
|
|
57
|
+
`ghcr.io/dosquartsdedocs/unaltraweb-mcp@sha256:908b4ce54c7bdf355e14ed55b31ed4b9baae319e211af90004a680d1d1cb8692`.
|
|
58
|
+
|
|
59
|
+
The four-profile populated-cache roundtrip also passed against the actual signed
|
|
60
|
+
candidate. The selected PDF stays at its published 0.5.0 digest, and computation,
|
|
61
|
+
capture and visual companions retain 0.4.0. See the
|
|
62
|
+
[delivery report](https://github.com/dosquartsdedocs/unaltraweb/blob/main/docs/agents/owner-closeout-76.md)
|
|
63
|
+
and [issue 76](https://github.com/dosquartsdedocs/unaltraweb/issues/76).
|
|
64
|
+
Strict release validation applies to the receipt/tag revision; subsequent
|
|
65
|
+
post-release launcher changes are ordinary source revisions, not new receipts.
|
|
66
|
+
|
|
67
|
+
### Previous 0.5.0 release
|
|
68
|
+
|
|
69
|
+
The previous coordinated core release is [**0.5.0**](https://github.com/dosquartsdedocs/unaltraweb/releases/tag/v0.5.0). It groups the integrated editorial
|
|
31
70
|
review, guided scaffold updates, caption-credit/image behavior and published
|
|
32
|
-
Diavisuals/Vegavisuals 0.4.0 acceptance.
|
|
33
|
-
|
|
71
|
+
Diavisuals/Vegavisuals 0.4.0 acceptance. Source-bound image/package workflows,
|
|
72
|
+
tag promotion and both Trusted Publishing jobs passed. Anonymous package downloads
|
|
73
|
+
match the receipt and clean native installations were checked.
|
|
34
74
|
Unchanged already-published computation and web-capture workers retain their own
|
|
35
75
|
0.4.0 versions and digests. New/pending worker candidates must still match the
|
|
36
76
|
coordinated release; an old mutable alias cannot qualify for reuse. The selected
|
|
@@ -41,19 +81,35 @@ at source `d857f8c9f5fea90cf450c0b30b4e77a37b541275` and is selected by digest
|
|
|
41
81
|
`sha256:9e0b3a45753c170b795e9a9d6df61580085c113436beac5bf6c8de69b6562097` in
|
|
42
82
|
both the factory and the consumer tuple. It is already published and tested, so
|
|
43
83
|
final candidate receipts cover the remaining ready package/core components.
|
|
44
|
-
The factory launcher
|
|
45
|
-
|
|
46
|
-
|
|
84
|
+
The 0.5.0 post-release factory launcher selected the MCP digest recorded in receipt
|
|
85
|
+
`3fa855378dcc61dc7b84b8b03812698042e02fed`:
|
|
86
|
+
`sha256:36d17edbade77edb40a687f6a744203c6329acb33fbc2eb255e88d9ff1a42c98`.
|
|
87
|
+
See [issue 69](https://github.com/dosquartsdedocs/unaltraweb/issues/69) for the
|
|
88
|
+
candidate, receipt, tag and package evidence.
|
|
47
89
|
|
|
48
90
|
`src/unaltraweb_mcp/component-contract.json` is the canonical versioned bill of materials. Its `consumer_integration` object is the sole source for the reviewed core Git revision, reusable deploy workflow, manual PDF image digest, and Vega renderer revision. Scaffold templates render that tuple atomically into consumer `Gemfile`, `Gemfile.lock`, and deploy workflow files. `component-contract.schema.json` defines schema version 1. Runtime loading and `scripts/validate_distribution.py` validate the complete document against that schema, then enforce semantic parity between versions, release tags, repositories, references, wheel contents, CLI availability, and consumer integration pins.
|
|
49
91
|
|
|
50
|
-
The BOM is an interoperability contract, not a bundle. The wheel contains
|
|
92
|
+
The BOM is an interoperability contract, not a bundle. The wheel contains its Python control/inspection modules, schema/BOM, clean package-owned scaffolds and a small host Docker launcher, described below. It does not include Ruby theme assets, Docker image layers, the factory's build/worker implementations, TeX, Chromium, computation environments, `diavisuals`, or `vegavisuals`.
|
|
51
93
|
|
|
52
|
-
The selected public core release is `0.
|
|
94
|
+
The selected public core release is `0.5.1`; earlier distributions remain immutable. Its BOM reuses immutable PDF, compute and web-capture worker digests and selects published `diavisuals v0.4.0` and `vegavisuals v0.4.0` through SHA-256-pinned wheel URLs. Companion references can describe either a provider/release-matching Git reference or a provider/release/version-matching wheel with its content hash. The wheel boundary remains external. The scaffold's Vega revision is the published `68c0b231402ae9485cc34ce530dc5239cb0ec194` commit. `distribution-check` validates structural integrity for normal CI. `distribution-release-check` blocks coordinated publication while any component is `pending` or `unavailable`; reviewed source authorized to produce final same-commit candidates is `ready`, while an already-published component is `released`. Final receipt values remain immutable after publication.
|
|
53
95
|
|
|
54
96
|
## Docker-First Hybrid Policy
|
|
55
97
|
|
|
56
|
-
|
|
98
|
+
### 0.5.1 component selection
|
|
99
|
+
|
|
100
|
+
The coordinated core identity is **0.5.1**: gem, wheel, base runtime and MCP
|
|
101
|
+
images were published together. The installed host launcher and runtime-aware
|
|
102
|
+
generated Bundler state are included. The unchanged PDF worker retains its
|
|
103
|
+
published 0.5.0 digest, alongside the 0.4.0 computation/capture workers and visual
|
|
104
|
+
companions. A released PDF can be reused only by full digest; new/pending workers
|
|
105
|
+
still require the coordinated version. The historical 0.5.0 receipt remains
|
|
106
|
+
unchanged. Signed image/package evidence is recorded in the 0.5.1 receipt;
|
|
107
|
+
promotion and anonymous-download checks passed before the post-release launcher
|
|
108
|
+
pin was advanced.
|
|
109
|
+
|
|
110
|
+
### Local delivery
|
|
111
|
+
|
|
112
|
+
GHCR is the canonical delivery channel for normal local use. The released package scaffold selects `ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.5.1`; existing sites can remain on their immutable previous release until deliberately updated. Its `make build`, `make serve` and `make test` targets mount the thin child site and run inside that image. The image contains both the installed Python control plane and the reviewed factory source at `/opt/unaltraweb`, so those targets load the theme as a path gem without downloading PyPI or RubyGems packages.
|
|
57
113
|
|
|
58
114
|
Factory registration uses a stricter pin. gContExt runs `mcp-build`, which inspects or pulls the full `MCP_RELEASE_IMAGE` digest, and `mcp-stdio` launches that exact image. Checkout builds use local `:dev` names by default through `mcp-image`, `mcp-check` and `mcp-smoke`, so they do not shadow public semver references unless a maintainer explicitly overrides them. The digest is advanced in a separate post-release change after each new receipt exists; candidate source continues to select the last completed release instead of attempting to embed an unknown self-digest.
|
|
59
115
|
|
|
@@ -67,6 +123,95 @@ The distribution keeps native channels for interoperability rather than making t
|
|
|
67
123
|
|
|
68
124
|
These remain real package boundaries: the MCP image installs the Python package and uses the core through Ruby's gem interface. The policy only makes their public registry installation optional for Docker users. It does not combine all toolchains into one image or duplicate worker layers in the wheel or gem.
|
|
69
125
|
|
|
126
|
+
### Installed Docker launcher
|
|
127
|
+
|
|
128
|
+
0.5.1 ships **`unaltraweb-mcp-docker`** and a complete host launcher
|
|
129
|
+
under the installation prefix's `share/unaltraweb-launcher/`. The published 0.5.0
|
|
130
|
+
wheel predates this addition; its receipt and bytes remain unchanged. An installed
|
|
131
|
+
wheel containing the launcher can use the already-published full GHCR runtime
|
|
132
|
+
without a local core checkout:
|
|
133
|
+
|
|
134
|
+
```bash
|
|
135
|
+
unaltraweb-mcp-docker prepare
|
|
136
|
+
unaltraweb-mcp-docker check
|
|
137
|
+
unaltraweb-mcp-docker smoke
|
|
138
|
+
unaltraweb-mcp-docker serve --project /absolute/consumer
|
|
139
|
+
```
|
|
140
|
+
|
|
141
|
+
The installed default selects its package's full MCP release image, currently
|
|
142
|
+
`ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.5.1`. It resolves that selection to the
|
|
143
|
+
local immutable image ID before executing. The checkout's `MCP_RELEASE_IMAGE`
|
|
144
|
+
is a separate digest pin advanced only after publication; it is not the installed
|
|
145
|
+
wheel's default. This avoids sending a new package back to an older MCP while
|
|
146
|
+
also avoiding an impossible self-digest in the candidate image/wheel.
|
|
147
|
+
`--image` selects a different explicitly prepared image for a test or a reviewed
|
|
148
|
+
adoption. `prepare` only inspects/pulls; `check` and `smoke` use the local image ID,
|
|
149
|
+
without pulling, building, mounting a consumer or starting a preview. `serve`
|
|
150
|
+
requires an explicit consumer or inherited `MCP_CONSUMER_WORKSPACE`; it starts one
|
|
151
|
+
labelled stdio container and preserves the canonical host-path mirror for workers.
|
|
152
|
+
`down --project /absolute/consumer` uses the same project-scoped cleanup helper.
|
|
153
|
+
|
|
154
|
+
`unaltraweb-mcp-docker path` locates the installed profile from wheel metadata;
|
|
155
|
+
`manifest` prints its discovery descriptor. The profile ships the same native
|
|
156
|
+
schema-v1 `mcp-factory.yml`, a small launcher-only Makefile, and the bootstrap,
|
|
157
|
+
project-ID, Docker CSV mount and cleanup scripts. Its `${factoryRoot}` is this
|
|
158
|
+
installed directory, and the declared `make -C` transport and lifecycle targets
|
|
159
|
+
remain usable. That directory can also be relocated as a unit and run with Make,
|
|
160
|
+
a POSIX shell, Linux core utilities and Docker, without host Python or Ruby.
|
|
161
|
+
The console adapter itself requires the wheel's Python interpreter. Linux/amd64
|
|
162
|
+
is the acceptance platform; other host/platform combinations remain unverified.
|
|
163
|
+
|
|
164
|
+
This adapter launches the **full container runtime**. The native `unaltraweb-mcp`
|
|
165
|
+
CLI keeps the exact wheel-only/factory-required boundary declared in the BOM.
|
|
166
|
+
Installing the adapter does not install Jekyll, workers or companion servers on
|
|
167
|
+
the host, register a client, update a consumer scaffold, or change an active MCP.
|
|
168
|
+
|
|
169
|
+
### Separate selections and compatibility evidence
|
|
170
|
+
|
|
171
|
+
The site Makefile's `MCP_IMAGE`, native Gem/core revision, PDF worker, global MCP
|
|
172
|
+
registration and companion selections are separate parts of an effective tuple.
|
|
173
|
+
TIG/TIGIT retain build defaults 0.4.0; Geodisseny retains 0.5.0. A global MCP
|
|
174
|
+
selection does not rewrite those defaults. Tests use synthetic sites,
|
|
175
|
+
image-specific test resources and dynamically allocated loopback preview ports.
|
|
176
|
+
|
|
177
|
+
Compatibility evidence is a set of tested tuples, not a continuous version range.
|
|
178
|
+
The [initial owner preparation report](https://github.com/dosquartsdedocs/unaltraweb/blob/main/docs/agents/owner-preparation-2026-09-29.md)
|
|
179
|
+
records all four 0.5.0 profiles, manual PDF coverage, the 0.4.0 comparison and
|
|
180
|
+
the reproduced retained-cache failure. The 0.5.1 correction is recorded in the
|
|
181
|
+
[follow-up report](https://github.com/dosquartsdedocs/unaltraweb/blob/main/docs/agents/owner-followup-76.md).
|
|
182
|
+
Range adoption belongs at
|
|
183
|
+
the native dependency/version checks, companion receipt checks and atomic
|
|
184
|
+
consumer-integration selection. Exact wheel hashes, image digests and published
|
|
185
|
+
receipts remain identity evidence even if future compatibility rules accept a
|
|
186
|
+
range. Central catalogue/range fields await the accepted hub integration.
|
|
187
|
+
|
|
188
|
+
### Generated Bundler state
|
|
189
|
+
|
|
190
|
+
0.5.1 keys generated dependencies by the effective Ruby/platform, Bundler,
|
|
191
|
+
installed gem inventory, core inputs and Bundler configuration, rather than a
|
|
192
|
+
mutable Docker tag. The offline resolver prepares a verified cache under
|
|
193
|
+
`tmp/unaltraweb-bundle/<identity>/`. Returning to an identity reuses its cache;
|
|
194
|
+
changing identities does not rewrite another runtime's lock. Credential-bearing
|
|
195
|
+
Bundler environment/configuration values contribute only hashes to the receipt.
|
|
196
|
+
|
|
197
|
+
New native build/preview targets execute with invocation-owned copies of that
|
|
198
|
+
generated state. Bundler can complete local default-gem checksum metadata without
|
|
199
|
+
rewriting the verified cache or disabling checksum validation. An
|
|
200
|
+
explicit `LOCAL_GEMFILE` is author-managed: its existing lock is required and
|
|
201
|
+
used frozen. Project `Gemfile`, `Gemfile.lock` and Bundler configuration are
|
|
202
|
+
preserved. Edited or incomplete generated caches fail for inspection instead of
|
|
203
|
+
being silently repaired. Failed preparation directories remain under `tmp/`.
|
|
204
|
+
|
|
205
|
+
For unchanged historical package Makefiles, the updated MCP prepares the same
|
|
206
|
+
runtime-specific cache and passes invocation-owned Gemfile/lock copies to the
|
|
207
|
+
old recipes. The retained `tmp/Gemfile.local.lock` remains untouched, so a later
|
|
208
|
+
0.4.0 build can use its original selection. This adapter requires the Makefile to
|
|
209
|
+
match its recorded scaffold baseline; authored Makefile customizations retain
|
|
210
|
+
their own dependency policy. Those consumers can deliberately adopt the updated
|
|
211
|
+
native targets through the normal reviewed scaffold workflow. New native targets
|
|
212
|
+
require a containing core/runtime; the already-published 0.4.0 and 0.5.0 images do
|
|
213
|
+
not acquire the correction automatically.
|
|
214
|
+
|
|
70
215
|
## Optional Wheel And Doctor
|
|
71
216
|
|
|
72
217
|
A clean `unaltraweb-mcp` wheel works without a factory checkout for `version`, `new-web`, top-level `doctor`, constrained source management, scaffold synchronization, `site-doctor`, HTML audit, and pure inspection where feasible. Examples include `mcp list-tools`, `starter-templates`, `detect-site`, `site-context`, `profile-check`, content/language/bibliography inventories, and `build-health`.
|
|
@@ -139,7 +284,7 @@ For that reason:
|
|
|
139
284
|
|
|
140
285
|
## Docker Runtime
|
|
141
286
|
|
|
142
|
-
Release `0.
|
|
287
|
+
Release `0.5.1` publishes the selected base/MCP runtime and packages while pinning the verified PDF worker and reusing unchanged specialized workers. Local maintainers continue to use explicit development names such as `unaltraweb:dev`; generated sites select the reviewed semver MCP image rather than `main` or `latest`.
|
|
143
288
|
|
|
144
289
|
The base runtime owns Ruby, Jekyll and system dependencies. The MCP image builds on its exact candidate digest and adds the full reviewed factory plus the Python package. Specialized workers remain separate. This keeps each layer focused without adding Chromium, TeX or computation stacks to every site; the coordinated core-image workflow still rebuilds and verifies runtime, MCP and manual PDF candidates together.
|
|
145
290
|
|
|
@@ -13,21 +13,21 @@ weight: 140
|
|
|
13
13
|
permalink: "/docker-image/"
|
|
14
14
|
nav_title: Docker Images
|
|
15
15
|
---
|
|
16
|
-
Release `v0.
|
|
16
|
+
Release `v0.5.0` currently publishes two core images. Published generated sites select the self-contained MCP/site image for normal local commands:
|
|
17
17
|
|
|
18
18
|
```text
|
|
19
|
-
ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.
|
|
19
|
+
ghcr.io/dosquartsdedocs/unaltraweb-mcp:0.5.0
|
|
20
20
|
```
|
|
21
21
|
|
|
22
22
|
It contains the Python control plane and the reviewed factory at `/opt/unaltraweb`. Its lower-level base is:
|
|
23
23
|
|
|
24
24
|
```text
|
|
25
|
-
ghcr.io/dosquartsdedocs/unaltraweb:0.
|
|
25
|
+
ghcr.io/dosquartsdedocs/unaltraweb:0.5.0
|
|
26
26
|
```
|
|
27
27
|
|
|
28
28
|
The base provides Ruby, Bundler, Jekyll system dependencies, ImageMagick, Node for ExecJS and Python tooling. Generated Make targets run in the MCP image and load layouts, styles and plugins as a path gem from `/opt/unaltraweb`. RubyGems remains an optional native Bundler channel rather than a download required by the local Docker path.
|
|
29
29
|
|
|
30
|
-
The `v0.
|
|
30
|
+
The `v0.5.0` receipt binds matching `unaltraweb:0.5.0` and `unaltraweb-mcp:0.5.0` references to their tested immutable digests. The semver aliases were promoted only after the coordinated receipt and tag checks completed.
|
|
31
31
|
|
|
32
32
|
gContExt prepares and launches the MCP image through the full digest in `MCP_RELEASE_IMAGE`. That post-release pin is separate from the semver scaffold reference and cannot be shadowed by checkout builds, which use local `:dev` names. A new release advances the pin only after its receipt records the published digest.
|
|
33
33
|
|
|
@@ -58,7 +58,7 @@ make mcp-image
|
|
|
58
58
|
make mcp-smoke-prebuilt MCP_IMAGE=unaltraweb-mcp:dev
|
|
59
59
|
```
|
|
60
60
|
|
|
61
|
-
Both core GHCR packages are public
|
|
61
|
+
Both core GHCR packages are public; their `v0.5.0` references resolve to the verified receipt digests.
|
|
62
62
|
|
|
63
63
|
## Computation Images
|
|
64
64
|
|
|
@@ -188,8 +188,8 @@ Selector-based screenshot authoring uses a separate Playwright image rather than
|
|
|
188
188
|
ghcr.io/dosquartsdedocs/unaltraweb-web-capture@sha256:0bf1bc67fe63e1440bffe708a168beefa11c54441650a871ab99380d362f7c1e
|
|
189
189
|
```
|
|
190
190
|
|
|
191
|
-
The `v0.
|
|
191
|
+
The `v0.5.0` contract reuses the already-published 0.4.0 worker by immutable digest. The image contains pinned Playwright/Chromium, the capture worker, the Python status controller, and the core visual sources used in fingerprints. `make web-capture-image` builds the explicitly named `unaltraweb-web-capture:dev` maintainer image; set `WEB_CAPTURE_IMAGE` to that name when testing it. The manual `Web capture image` workflow publishes default-branch, commit, and semver/release tags to GHCR.
|
|
192
192
|
|
|
193
|
-
Published `v0.
|
|
193
|
+
Published `v0.5.0` scaffolds consume `ghcr.io/dosquartsdedocs/unaltraweb-manual-pdf@sha256:9e0b3a45753c170b795e9a9d6df61580085c113436beac5bf6c8de69b6562097`. `manual-pdf-image` reuses or pulls the selected image instead of rebuilding it locally. Maintainers use `make manual-pdf-image-dev` and then pass `MANUAL_PDF_IMAGE=unaltraweb-manual-pdf:dev` for local PDF runtime changes.
|
|
194
194
|
|
|
195
195
|
Rendering creates an ephemeral Docker `--internal` network shared only by Jekyll and Chromium, keeps browser requests on the preview origin, blocks service workers, popups, and WebSockets, drops Linux capabilities, uses a read-only container root and bounded resources, and writes only the declared PNG/SVG outputs under the mounted project. Ordinary checks run without browser execution or network access.
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: Import A Retained Letter
|
|
3
|
+
description: Verify and retain a Carta letter bundle, display its PDF on the web and include it in a manual.
|
|
4
|
+
lang: en
|
|
5
|
+
ref: retained_documents
|
|
6
|
+
profiles:
|
|
7
|
+
- unaltredocs
|
|
8
|
+
documentation_profiles:
|
|
9
|
+
- local-authors
|
|
10
|
+
- core-developers
|
|
11
|
+
section: Build A Site
|
|
12
|
+
weight: 240
|
|
13
|
+
permalink: /retained-documents/
|
|
14
|
+
nav_title: Retained Documents
|
|
15
|
+
---
|
|
16
|
+
|
|
17
|
+
A retained letter combines its original PDF with the source, rendering inputs and
|
|
18
|
+
provenance needed to inspect its origin. The importer keeps that complete unit in
|
|
19
|
+
the receiving repository and creates a native page or chapter referencing the PDF.
|
|
20
|
+
The website displays the original; a manual PDF includes all its pages.
|
|
21
|
+
|
|
22
|
+
This capability belongs to the **0.6.0 development increment**. It requires a
|
|
23
|
+
containing Python package and Jekyll core, plus the matching PDF worker for manual
|
|
24
|
+
output. The published 0.5.1 runtime predates it. Changing the global MCP selection
|
|
25
|
+
does not update a site's Gemfile, Makefile or PDF-worker selection.
|
|
26
|
+
|
|
27
|
+
Native gem builds need Python with `PyYAML>=6,<7`, `pypdf>=6,<7` and
|
|
28
|
+
`markdown-it-py>=3,<5`. The containing MCP/PDF images provide these dependencies;
|
|
29
|
+
the containing reusable deployment workflow installs the PDF/text parsers when
|
|
30
|
+
retained imports are present.
|
|
31
|
+
|
|
32
|
+
## Supported Input
|
|
33
|
+
|
|
34
|
+
The receiving profile accepts leaf `letter-pdf-v1` bundles from **Carta
|
|
35
|
+
0.3.0rc1**, using the existing artifact handoff v1 envelope. Verification covers
|
|
36
|
+
the supplied sender SHA-256, complete file inventory, retained render recipe,
|
|
37
|
+
templates, source references, drawable resources and renderer identity. PDF
|
|
38
|
+
inspection is bounded and rejects encrypted files, embedded or external files,
|
|
39
|
+
JavaScript and unsupported actions. Internal destinations and textual HTTP,
|
|
40
|
+
HTTPS and email links are supported.
|
|
41
|
+
|
|
42
|
+
Renderable metadata is checked independently of the retained Pandoc AST. A
|
|
43
|
+
resealed bundle with an unretained local link in a subject or author field is
|
|
44
|
+
rejected even when its older parsing evidence does not mention that link.
|
|
45
|
+
|
|
46
|
+
Limits are 64 MiB for the payload unit, 32 MiB for the PDF and 1–64 pages. The
|
|
47
|
+
supported source subset excludes body images, raw markup, TeX, math and citations;
|
|
48
|
+
attachments remain text labels. Composite bundles, edited PDF variants and
|
|
49
|
+
Diapora composition require separate receiving profiles.
|
|
50
|
+
|
|
51
|
+
Obtain the bundle's expected SHA-256 through the sender's trusted handoff. A hash
|
|
52
|
+
computed only from an unknown local manifest establishes consistency, not its
|
|
53
|
+
origin. Importing never executes the retained recipe or contacts the producer.
|
|
54
|
+
|
|
55
|
+
## Import Into A Consumer
|
|
56
|
+
|
|
57
|
+
Start with an initialized consumer Git repository. Place the complete incoming
|
|
58
|
+
bundle under a workspace-relative directory such as `tmp/incoming/letter/`.
|
|
59
|
+
The recovery area under `tmp/` must be ignored and untracked; durable destinations
|
|
60
|
+
must be eligible for version control.
|
|
61
|
+
|
|
62
|
+
Review a plan using the installed CLI. Here `BUNDLE_SHA` is the sender's verified
|
|
63
|
+
manifest digest:
|
|
64
|
+
|
|
65
|
+
```bash
|
|
66
|
+
unaltraweb-mcp --project /absolute/consumer mcp import-artifact-bundle \
|
|
67
|
+
--path tmp/incoming/letter/bundle.json --sha256 "$BUNDLE_SHA" \
|
|
68
|
+
--import-id correspondence --content-path _chapters/en/correspondence.md \
|
|
69
|
+
--title "Retained correspondence"
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
To apply the reviewed request, repeat it with `--apply --confirm-import`.
|
|
73
|
+
The MCP equivalent is `import_artifact_bundle` with `dry_run=false` and
|
|
74
|
+
`confirm_import=true`; its default is a read-only plan.
|
|
75
|
+
|
|
76
|
+
Choose a new Markdown destination under `_pages/`, or `_chapters/` for a manual,
|
|
77
|
+
or `_documentation/` for a documentation site. An executable source owning the
|
|
78
|
+
same Markdown basename blocks creation. The generated document starts as a draft
|
|
79
|
+
in the consumer's default language, with a literal local permalink.
|
|
80
|
+
|
|
81
|
+
The resulting paths are:
|
|
82
|
+
|
|
83
|
+
| Path | Purpose |
|
|
84
|
+
| --- | --- |
|
|
85
|
+
| `.unaltraweb/artifacts/correspondence/bundle/` | Complete, unchanged incoming seal, outside the web output |
|
|
86
|
+
| `.unaltraweb/artifacts/correspondence/integration.json` | Standard v1 integration record and byte-preserving PDF mapping |
|
|
87
|
+
| `.unaltraweb/artifacts/correspondence/binding.json` | Native content path and integration-record digest |
|
|
88
|
+
| `assets/documents/correspondence.pdf` | Public PDF, identical to the retained original |
|
|
89
|
+
| `_chapters/en/correspondence.md` | Native chapter with the retained-document component |
|
|
90
|
+
|
|
91
|
+
Version the complete durable unit together. The incoming directory and ignored
|
|
92
|
+
recovery journal are not runtime dependencies. The retained archive is excluded
|
|
93
|
+
from website output, but remains ordinary repository content.
|
|
94
|
+
|
|
95
|
+
## Edit And Render The Native Document
|
|
96
|
+
|
|
97
|
+
Add explanatory prose to the generated page or chapter while preserving its
|
|
98
|
+
literal permalink and component:
|
|
99
|
+
|
|
100
|
+
{% raw %}
|
|
101
|
+
```liquid
|
|
102
|
+
{% retained_document correspondence %}
|
|
103
|
+
```
|
|
104
|
+
{% endraw %}
|
|
105
|
+
|
|
106
|
+
On the web, the component renders a PDF object with a labelled download link.
|
|
107
|
+
The build checks the bound page's exact local PDF URL and the emitted PDF bytes.
|
|
108
|
+
Exposing the retained archive in the website is an error. In a manual, the PDF
|
|
109
|
+
builder includes every original page and fingerprints the entire retained unit
|
|
110
|
+
and its checker implementation. A controller/worker mismatch therefore fails
|
|
111
|
+
freshness verification rather than silently accepting an older checker.
|
|
112
|
+
|
|
113
|
+
Run `artifact_import_check` or the CLI equivalent before building:
|
|
114
|
+
|
|
115
|
+
```bash
|
|
116
|
+
unaltraweb-mcp --project /absolute/consumer mcp artifact-import-check
|
|
117
|
+
unaltraweb-mcp --project /absolute/consumer mcp artifact-import-check --output-folder _site
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
`site_check` and `site_doctor` include the native integrity check. For a local
|
|
121
|
+
manual review, use `manual_pdf_preview_prepare`, then `build_site` and
|
|
122
|
+
`preview_start`. Review the web page and composed PDF, then clean only the
|
|
123
|
+
receipt-owned preview copies through `manual_pdf_preview_clean`.
|
|
124
|
+
|
|
125
|
+
## Preservation And Recovery
|
|
126
|
+
|
|
127
|
+
An identical reimport preserves authored prose. A changed mapped PDF, conflicting
|
|
128
|
+
destination, unsafe path or modified seal blocks the operation; existing files
|
|
129
|
+
are never overwritten. After an interrupted import, unchanged partial files may
|
|
130
|
+
be adopted by an explicit retry of the same request. Differing partial files
|
|
131
|
+
require inspection. The operation retains its prepared tree and journal under
|
|
132
|
+
`tmp/unaltraweb-artifact-imports/` and performs no destructive rollback.
|
|
133
|
+
|
|
134
|
+
The native check verifies references and content after the incoming producer copy
|
|
135
|
+
has been removed or the receiving repository has moved. It also detects missing
|
|
136
|
+
content, incomplete retention and altered mappings. The generic v1 verifier can
|
|
137
|
+
independently inspect `integration.json`; it does not replace the native source
|
|
138
|
+
and rendered-output checks.
|