# Dev architecture: JATS article gateway

Status: dated JATS pilot snapshot, 18 September 2026. This document describes
the initial isolated development environment. A larger scheduled JNIS JATS
private-stage feed and daily usage reporting were added later; see the
[current operator guide](OPERATIONS_REPORTS_AND_CONTENT_PULLS.md) and
[architecture flows](C4_ARCHITECTURE.md#current-dev-scheduled-operations).
Dev has separate credentials, R2 objects, D1 metadata, releases, collections,
indexes and customer scopes from live and from the original evaluator.

## Corpus and invariants

The dev fixture contains 100 JNIS JATS v6 articles and 25 OA JATS v7 articles. The running adapter is JATS v7. Each admitted source has an immutable source hash and source/version identity. The raw publisher XML and the canonical serving document are stored in R2. Canonical documents use the `bmj-content/1` schema; D1 stores rebuildable metadata and search projections.

The canonical article retains abstract sections, body blocks, tables, figures, citations and references. References are delivered with complete article content, but reference text and bibliography fields are excluded from topic search. Figure and supplementary binary assets remain source links and are not mirrored in this dev fixture.

## Runtime shape

The content-admin Worker is the dev boundary for authenticated REST and stateless MCP requests, the admin ingestion API, and per-document Workflows. R2 is the source and canonical-content store. D1 owns publication metadata, authors, publication dates, collection membership and FTS5 BM25 projections. Collection access is applied while selecting permitted release versions, so search and delivery never escape the caller's customer scope.

The current JATS path makes no AI calls and does not create vector embeddings. Its deployed retrieval is lexical D1 FTS5 BM25. Legacy paragraph/vector and AI Search paths remain present for the existing evidence corpus as separate optional paths. Sidecars and CI pass-through are future work and are not part of the deployed dev flow.

## Public demonstration tour

The public demonstration is a synthetic, read-only tour of the product surface. Open [`/demo`](/demo) for the static tour or [`/demo/download`](/demo/download) for the allowlisted ZIP bundle. The bundle contains no API key and no JNIS source data; it is safe to use as a presentation aid. Run the local demo server when reproducing guided recordings. The server retains the latest recording snapshot until it is overwritten or deleted; no automatic expiry is implemented.

## Ingestion

An authorised local importer fetches and preflights source XML, then uploads it to the dev Worker. The Worker writes immutable source bytes and starts a document Workflow. The adapter emits the canonical article and metadata; the Workflow stores the canonical version, projects D1 metadata/FTS and records readiness. A source or adapter-version change creates a new immutable document version; existing source objects are not rewritten. Operators separately choose and publish index generations.

The verified named collections are `jnis-100` and `oa-jats-25`. The importer is an operator-run local tool, not a scheduled Cloudflare pull connector. Sidecar metadata feeds, CI pass-through and semantic indexing for this JATS path are planned extensions.

## Search and delivery contract

`GET /v1/articles` is a thin candidate/frontmatter interface over D1. With `include=frontmatter`, it returns complete abstract and bibliographic metadata without materialising full article text. Terms search uses any unquoted term as an OR query; quoted phrases are matched as phrases. Explicit `author`, `year` and `date_basis` filters are applied as metadata constraints and are never relaxed. `search_mode` supports `terms`, `bibliographic` and `auto`; ambiguous auto interpretation reports clarification rather than silently choosing a different constraint.

Index and query text use matching stemming and UK/US spelling normalization. There is no automatic typo correction or query relaxation. The current FTS5 BM25 configuration uses k1=1.2, b=0.75 and title/abstract/body/keyword weights of 5/2/1/3. Index statistics include all indexed version rows; scores are meaningful within the same index revision. See the [bibliographic guide](JATS-bibliographic-search-2026-09-18.md) for name/year interpretation and its limits.

`GET /v1/frontmatter` provides metadata directly. `GET /v1/articles/:id` delivers a scoped complete article as structured JSON, canonical Markdown, or raw JATS. Complete delivery includes tables, figures, citations and references and is versioned; an oversized article returns an explicit size error. Collection membership and release scope are enforced for every read.

MCP exposes the same article contract through `search` (auto by default, with complete abstracts and interpretation details) and `fetch` (complete Markdown with metadata), alongside the compatibility `search_articles` and `get_article_content` tools. Legacy MCP search tools and the legacy `max_excerpt_chars` evidence limit remain for the older evidence path; they do not limit complete JATS delivery.

## Diagrams

The current diagrams are embedded in the dev architecture section of `/admin/docs` and are also available through the diagram viewer:

- [Dev system context](diagrams/dev-context.svg) · [Mermaid source](diagrams/dev-context.mmd)
- [Dev containers](diagrams/dev-containers.svg) · [Mermaid source](diagrams/dev-containers.mmd)
- [Dev ingestion and delivery sequence](diagrams/dev-ingestion-delivery.svg) · [Mermaid source](diagrams/dev-ingestion-delivery.mmd)

The other embedded diagrams on the admin page are general or legacy architecture references. They remain useful for the wider gateway, but should not be read as the current dev JATS source of truth.

## Code map

| Concern | Current implementation |
| --- | --- |
| Upload admission and source identity | `workers/content-admin/src/ingestionService.ts` |
| Durable document execution | `workers/content-admin/src/workflow.ts` |
| JATS v7 adapter and canonical model | `workers/content-admin/src/publications/jats.ts`, `model.ts` |
| D1 metadata and FTS projection | `workers/content-admin/src/publications/repository.ts` |
| Candidate/frontmatter search | `workers/content-admin/src/publications/list.ts` |
| Scoped complete delivery | `workers/content-admin/src/publications/delivery.ts` and `content.ts` |
| MCP article tools | `workers/content-admin/src/mcp.ts` |
