Export
Export research results as HTML, PDF, Markdown, DOCX, slides, run records, or evidence packs
Research results can be exported in seven formats via the /results/\{result_id\}/export endpoint.
Formats
| Format | Content-Type | Use Case |
|---|---|---|
html | text/html | Browser viewing, embedding, sharing |
pdf | application/pdf | Download, print, archive |
markdown | text/markdown | Raw content, further processing |
docx | application/vnd.openxmlformats-officedocument.wordprocessingml.document | Editable Word document |
slides | text/html | Self-contained reveal.js presentation deck |
run-record | application/json | Shared run record and explicit unassessed claims |
evidence-pack | application/zip | Unsigned evidence archive with offline verification |
Usage
HTML Export
curl -H "X-API-Key: your-key" \
"https://api.krawl.sh/results/RESULT_UUID/export?format=html"Supports a theme parameter for light or dark mode:
# Dark theme
curl -H "X-API-Key: your-key" \
"https://api.krawl.sh/results/RESULT_UUID/export?format=html&theme=dark"The HTML export is a self-contained page with:
- Full markdown-to-HTML rendering
- Styled headings, tables, lists, code blocks
- Source list with URLs and source types
- Research metadata (query, mode, duration)
PDF Export
curl -H "X-API-Key: your-key" \
"https://api.krawl.sh/results/RESULT_UUID/export?format=pdf" \
-o report.pdfThe PDF includes:
- Title and metadata header
- Full report content with formatting
- Sources appendix with URLs and source types
- Generated via fpdf2 with HTML subset rendering
- Fallback to plain text if HTML rendering fails
Markdown Export
curl -H "X-API-Key: your-key" \
"https://api.krawl.sh/results/RESULT_UUID/export?format=markdown" \
-o report.mdReturns the raw markdown report as generated by the synthesis model. This is the most portable format for further processing.
DOCX Export
curl -H "X-API-Key: your-key" \
"https://api.krawl.sh/results/RESULT_UUID/export?format=docx" \
-o report.docxReturns an editable Microsoft Word document with the title, metadata, formatted report body, and a sources appendix.
Slides Export
curl -H "X-API-Key: your-key" \
"https://api.krawl.sh/results/RESULT_UUID/export?format=slides" \
-o report-slides.htmlReturns a self-contained reveal.js HTML deck that turns the report into a presentation. Open it in any browser — no build step required. Long sections are split across continuation slides automatically.
Parameters
| Parameter | Type | Default | Options |
|---|---|---|---|
format | string | "html" | html, pdf, markdown, docx, slides, run-record, evidence-pack |
theme | string | "light" | light, dark (HTML only) |
Filenames
Downloaded files use a sanitized version of the research query as the filename:
what-is-the-current-state-of-ai-agents.pdfwhat-is-the-current-state-of-ai-agents.mdwhat-is-the-current-state-of-ai-agents.docxwhat-is-the-current-state-of-ai-agents-slides.html
HTML and slides exports use Content-Disposition: inline (displayed in browser). PDF, Markdown, and DOCX use Content-Disposition: attachment (downloaded).
Getting a Result ID
Result IDs are returned in the result SSE event during research, and can be retrieved from:
# List all results
curl -H "X-API-Key: your-key" https://api.krawl.sh/results
# Get a specific result
curl -H "X-API-Key: your-key" https://api.krawl.sh/results/RESULT_UUIDEvidence time and access
Research sources carry optional retrieved_at (UTC), published_date,
updated_date, date provenance, access_status, source_record_id and
temporal_status. Missing fields on older reports mean unknown; never assign
export time as retrieval time. Access states are inspected_text,
partial_excerpt, provider_summary, metadata_only, fetch_failed, or
unknown. These describe available evidence, not claim support or truth.
A recent fetch does not make an old article current. Summary/metadata-only
results do not establish that the original text was read.
Optional source_policy.as_of sets a UTC evidence cutoff; dates after it are
quarantined in quarantined_sources, outside synthesis. Without it the cutoff
is research start. This is not a historical web archive; undated content
remains uncertain. See evidence methodology.
Evidence coverage
The optional evidence_coverage result field gives descriptive counts of unique
exact URLs discovered, explicitly fetched, retained, referenced in outgoing
model input, and cited. Stages overlap: a retained search snippet may never
have had its original page fetched. It also reports explicit failed/unavailable
fetches, unknown fetch/access states, retained-host concentration, missing
publication dates and their known range. A model-input reference may contain
only metadata or a short excerpt; a citation is not a support verdict.
These counts do not establish representative sampling or correct selection
bias. Hostnames do not prove independent origins; mirrors may share a publisher.
Old reports without this field have unknown coverage. No extra LLM call is made;
the measured instrumentation overhead is reported as measurement_overhead_ms,
not a guarantee of zero added latency. See evidence methodology.
Run record
Download /results/{result_id}/export?format=run-record with the owning API key.
The JSON bundle uses schema version 1 and includes the run, claim candidates,
source observations, a report snapshot, and the original Markdown. It is
compatible with the shared Claude Code run-record schemas. Every hosted claim
starts unassessed; this export does not judge support or reconstruct saved
page bytes. Empty events and ledger arrays mean those details were not retained,
not that the run was free. Legacy observation dates remain unknown.
MCP export_result accepts the same format and returns JSON text inline. The
read-only export does not add storage or make ZDR runs retrievable.
Schemas: bundle. From the repository, validate a downloaded bundle offline:
uv run --project apps/api --locked python scripts/validate_run_record.py report-run-record.jsonEvidence pack
Use format=evidence-pack to download an unsigned ZIP with a versioned
manifest, the run record, and instructions for offline verification. The
manifest binds exact stored bytes with SHA-256. It preserves source access
states and observation times; an export timestamp is never substituted for a
missing retrieval time. Hosted results have no retained raw page copies, so
those copies are explicitly unverifiable. An export does not fetch them.
curl -H "X-API-Key: your-key" \
"https://api.krawl.sh/results/RESULT_UUID/export?format=evidence-pack" \
-D export-headers.txt -o report.evidence.zipThe owning key is required for retained results. Wrong-owner and deleted
results return 404. The response is application/zip, with Cache-Control: private, no-store and X-Krawl-Evidence-SHA256. Keep private packs private.
This operation creates no retained server-side archive or new source copy.
Current research SSE and MCP results include their server-allocated id,
query, mode, created_at and measured duration_seconds. The ID identifies
the logical result; it is not proof of persistence for a ZDR or failed-save run.
Cutoff and quarantined source observations are preserved in inline exports.
For a streamed result, including a ZDR result, send the full public result
object in {"result": ...} to POST /exports/evidence-pack. It must include
id, query, mode, report (or markdown), sources, created_at and
duration_seconds. The request body is limited to 1 MiB. The server projects
only public result fields and builds the archive in memory; it never stores the
query, content, source URL hashes, archive, or idempotency response. It sends no
webhook and makes no model or source-provider call. You may save the returned
archive on your own device. Supplying an object does not authenticate its
origin or assertions.
MCP export_result accepts format: "evidence-pack" and exactly one of
result_id or result. The ZIP is returned in content_base64, with sha256,
manifest_sha256, size_bytes, unavailable_copies, and unsigned: true.
Other export formats continue to use a retained result_id.
Verify offline
From a checkout, install the independent core and run:
uv run --package krawl-core krawl-evidence verify report.evidence.zip
# Optionally pin a digest obtained through a trusted channel:
uv run --package krawl-core krawl-evidence verify report.evidence.zip --sha256 DIGESTThe verifier has no API credentials or network requirement and extracts no files. Exit 0 means the declared bytes, internal references and available cited passages match. Exit 2 means some source copies are unavailable; the output identifies each source and report version. Exit 1 means invalid bytes, metadata, references, passage offsets or archive structure. These codes do not measure factual correctness, source independence or publisher identity. An attacker who can replace the entire unsigned archive can replace its hashes. A trusted external digest detects replacement of the whole archive.
For local Claude Code runs, the workbench's Download evidence pack includes all report versions and already saved copies. The command-line equivalent is:
uv run --package krawl-core --extra engine krawl-engine export \
--project /path/to/project --output report.evidence.zipThe CLI creates a new private file (0600); it refuses to overwrite a file. Missing local captures remain explicitly unverifiable. The export preserves existing retention choices and does not acquire new rights to redistribute a source. Use only copies you are entitled to retain and share.
Manifest schema.
The format is version 1: SHA-256 over exact raw bytes and UTF-8 extracted text;
json-utf8-sort-v1 encodes JSON with sorted keys, compact separators, unescaped
Unicode, no non-finite numbers, and one trailing newline. Passage offsets count
Unicode code points in the extracted text. The verifier rejects duplicate JSON
keys, traversal, symlinks, unexpected members, and oversized archives (64 MiB
content, 1 MiB manifest, 4,096 entries). It supports stored and deflated ZIP
members without extracting them.
Signed origin attestations are future work. They would require defined issuer identity and claim semantics, trusted roots, signing-key custody and rotation, revocation and compromise handling, and client verification policy. This unsigned format provides none of those assurances.