openstamps
v1.0.0-rc.1
Published
Check a Cosmic Time Stamp (.cts) on your own machine: npx openstamps check file.cts [original]. Offline, no dependencies, checks only — it never stamps.
Maintainers
Readme
openstamps
Check a Cosmic Time Stamp on your own computer.
npx openstamps check report.pdf.cts report.pdfThat answers two questions: is the stamp intact, and is report.pdf the same file that was sealed? It runs offline:
nothing is sent anywhere. It has no dependencies. It only checks — it cannot make a stamp.
Needs Node.js 20 or later.
What the answer means
Every answer is one of three faces. There is no tick and no "pass".
| Face | Means | Exit status | |---|---|---| | ◇ not refuted | The stamp holds on this machine, and nothing checked contradicts it. | 0 | | ✕ refuted | Something checked contradicts it: the stamp was altered, a timestamp in it does not hold, or the file you gave is a different file. Do not rely on it. | 1 | | ◔ not checked | Something could not be checked here, and the answer says why (for example: the file is not a stamp, or it is a newer form than this program reads). This is never a finding against the file. | 2 |
A stamp fixes bytes and a time window. It never shows that the content is true, who made it, or where it was made. "Not refuted" is not "true".
Commands
npx openstamps check <stamp> [original]
<stamp>is a.ctsfile (JSON) or a.cstpfile (the compact binary form).[original]is the file you think was sealed. It is hashed on your machine; only its SHA-256 is compared.--sha256 <hex>compares with a SHA-256 you already have, instead of a file.--jsonprints the whole answer as JSON.
What is checked: the stamp's 152-byte core and its identity; the Merkle root over its proof entries; the claims and dates it commits; each RFC 3161 timestamp in it, against the public key this program carries for that timestamp authority, and that the timestamp was issued for this stamp and not copied from another; and your original's SHA-256.
What is not checked here, and is listed under "not checked" in the answer:
- the drand beacon round's own signature, which a stamp file does not carry — the "not before" time is read from the sealed round, not re-checked against drand (that needs the network);
- a timestamp from an authority this program has no key for;
- the twelve sky positions from an ephemeris table (see
gradefor what can be recomputed without one).
npx openstamps grade <stamp>
Reads the sky sealed in a stamp and, when the stamp commits a place, works out where the Sun was at that place and moment — its height, its direction, the shadow a vertical stick would cast, and whether it was day, twilight or night — using nothing but trigonometry on three sealed numbers (the Sun's longitude, the Earth's rotation angle and the tilt of its axis). No ephemeris is needed.
If the stamp also records a sighting of the Sun, or the direction and length of a shadow, grade compares it with that
prediction:
- inside the tolerance: ◇ not refuted — anyone who computes the sky can write the same numbers, so this is never a pass;
- outside it, or a Sun that would have been below the horizon: ✕ refuted;
- a Moon or planet sighting: ◔ not checked — those need an ephemeris, which this program does not include.
Options:
--tol <degrees>your tolerance on each axis (default 2°, never more than 30°). On top of it the grader always allows for what its own prediction leaves out: atmospheric refraction (about 0.6° at the horizon), a 0.025° position error, and near the zenith, where direction means nothing, any azimuth.--place <lat>,<lon>when the stamp commits no place: prints the Sun at a place you give, marked as a reading. It never grades anything, because a place given beside a stamp is not sealed in it.
npx openstamps capsule <file.cstp.txt>
Checks a CSTP-CAPSULE/1 "postcard" — the short text form of a stamp made for an AI's context. The stamp embedded in it is decoded, and the whole postcard is re-drawn from that stamp and compared line by line: an added, edited or dropped line is ✕ refuted; a postcard that is exactly what its stamp draws is ◇ not refuted. The answer includes the checker's own drawing — give an AI that, never the file you were handed, because anyone can copy a postcard's wording. No line of the file is repeated in the answer. The embedded stamp's own check is shown separately.
npx openstamps mcp
Runs the checker as an MCP server over standard input and output, for AI agents. It offers two tools, check_seal
and check_capsule, and nothing that stamps. For example, in an MCP client's configuration:
{ "mcpServers": { "openstamps-check": { "command": "npx", "args": ["-y", "openstamps", "mcp"] } } }The answers are faces with reasons, never true/false flags, because a model reads a flag and stops reading.
As a library
import { readFile } from "node:fs/promises";
import { checkStamp } from "openstamps";
const answer = await checkStamp({ stamp: await readFile("report.pdf.cts") });
console.log(answer.word, answer.said); // e.g. "◇ not refuted", and what that rests ongradeStamp, checkCapsule, createMcpHandler and the open grader's functions (openSunFromAngles, openGrade, …)
are exported too.
Exit status
0 ◇ not refuted · 1 ✕ refuted · 2 ◔ not checked · 64 wrong usage · 66 an input file could not be read ·
70 this program failed (never a verdict about any file).
Licence
Apache-2.0, © 2026 Protosonic OÜ — see LICENSE. Third-party code bundled inside is listed in THIRD-PARTY-NOTICES.md, and
every bundled source file is listed in dist/BUNDLE-INPUTS.json. The readable src/reference-reader.mjs is the licensed check-only extraction; READER-EXTRACTION.json records its provenance. Its original mixed producer/reader modules are not licensed wholesale. The stamp format, CSTP v1, is openly specified; a
program that reads it may say it implements CSTP v1, but "OpenStamps" is Protosonic's name.
This program reports what it checked. Relying on a stamp is the reader's own decision.
