Skip to content
Provider Ledger

Data as at

How to check this record

This page is not a green tick to trust. It sets out the exact method behind every hash shown on this site, and the values this run currently publishes, so the check can be done independently of this site.

The hash chain

Every recorded change is one line in an append-only log: a provider added, a provider removed or a page that changed. Each line carries event_hash, the SHA-256 of that event’s own fields (sorted keys, no inserted whitespace, the event_hash field itself excluded from what is hashed), and prev_event_hash, which must equal the event_hash of the line immediately before it. The very first line in a log points to 64 zero characters rather than to another event, because there is no event before it.

Editing, reordering or deleting any past line breaks this chain from that point forward, because every later line still claims the hash of what used to be there. A correction is never made by changing a line; it is a new line, dated when it was made.

The start of the current chain

The earliest event this record holds: the one line whose prev_event_hash is 64 zeros rather than another event’s hash.

Recorded
Event type
baseline
Source
fr_pa_list
Previous event hash
000000000000…(genesis)
Event hash
b9d182d18351…

Checking it without this site

Three checks, each independent of anything this site says about itself:

The published files, and where to fetch them

The chain check, and the checks of the published files against one another, can be run on files this site serves, as they were when this page was built. They are copied, byte for byte, from the export directory the build read; no second copy is kept, so what is served cannot drift from what was published. They are the files of the run dated .

These paths are fixed. They are the file names the export contract gives, under /exports/, and they will not move: a script that fetches one today will fetch the same path later. A path is added when the contract adds a file and is not taken back. The contract itself is served at /schema/exports.schema.json.

What is not served, and why

This site serves none of the publishers’ own files (the snapshots), whatever a publisher’s terms say, because whether a file may be republished is decided source by source and this site does not make that decision. The portable archive carries some of them. Each source declares a snapshot_policy in countries.json, and only the word public lets the engine keep the file where the archive can carry it, listed as included in snapshots/MANIFEST.sha256. Any other value, or none, keeps it out, and the manifest lists the file’s digest as absent.

A source declares private for one of two reasons, and either is enough.

So a withheld file does not show that the publisher’s terms are restrictive, and an open licence does not show that the file is published.

The register has read 2 sources in this set. 1 declares public, and the file of the other one is withheld:

If this table is wider than the space it has here, scroll it sideways to see every column.

Sources in this set that the register has read and whose file is withheld from the portable archive, with the snapshot policy each declares and the reuse terms the register recorded for it.
SourcePolicy declaredTerms the register recordedLast read
fr_pa_list FranceprivateLicence Ouverte / Etalab 2.0 (https://www.impots.gouv.fr/mentions-legales): 'les informations de ce site sont proposés sous licence ouverte Etalab 2.0'; site graphics excluded.

countries.json records each source’s policy and the terms the register recorded for it. It does not record which of the two reasons applies, so this page does not say. Where the terms recorded allow the file to be republished, as an open licence does, they are not the reason, and the file is withheld for what it holds.

A further 61 sources are declared in countries.json and the register has not read them, so there is no file of their own to carry or to withhold. The page for each country lists the policy it declares.

What this record holds of a withheld file is its SHA-256 digest, on each event and each withdrawal row that cites one. A reader can check it only against a copy of the file, and the publisher’s own copy is the one most readers can reach, so the check holds while the publisher serves those bytes and no longer.

For a list, the engine also records parsed_sha256: the SHA-256 of the records it built from the file, names included and nothing the record drops. Since the engine began to record it, it has been on each baseline event, which ties the names to the count the baseline states, and in the observation seal of a day that recorded no event, which names the digest of what each source the run read yielded. It is a second claim about the same file and not a replacement for the first. providers.json publishes a reduced form of each record, so the digest cannot be recomputed from the published files, and only a reader who holds the publisher’s file can reproduce it.

The engine’s own log (data/changelog.jsonl), the timestamp proof files and the seals (run digests and observation seals) are in the portable archive, not here. The build checks the output for any of these, or for any path it does not recognise, and stops rather than publish it.

What dates a run

A seal is a short text file the engine writes into data/digests/, named from the run’s instant, and submits to public timestamp calendars using the OpenTimestamps standard. The calendars anchor it into the Bitcoin blockchain, which gives a proof that these exact bytes existed no later than a given time, checkable by anyone through the OpenTimestamps method, independently of this site. The proof (.ots) and the state of the stamp (.status) are files beside the seal. What a seal says depends on what the run did, and a run is one of three kinds. A day, here, is the UTC day of the run’s instant.

Latest run
Run digest
2280b65fcda2…
Timestamp
stampedSubmitted to public timestamp calendars; the Bitcoin attestation is not complete yet.

A stamp has two stages. When a seal is submitted the calendars return a pending attestation, which is the state stamped. The Bitcoin attestation follows once the transaction that carries it confirms, which can take hours, and a weekly upgrade pass collects it for every seal whose state is stamped and changes the state to upgraded. That pass skips a seal in any other state. A seal whose stamp failed (stamp_failed), or that was made with no timestamp client (pending_no_ots), has no pending attestation to collect. The pass skips it and the engine does not stamp the same bytes a second time, so every event it names stays in the chain and only the independent proof of when it existed is missing. A day with no seal has nothing for the pass to collect.

What this proves, and what it does not

The checks above compare files with each other and with the stamp they carry. What they can establish depends on which files the reader holds, so this section answers for two readers separately. One holds the seven flat published files. The other holds the portable archive, which carries those same files and also the whole changelog, data/changelog.jsonl. They do not get the same answer to every question, and neither is told more than it can be: a record that says what it cannot show is worth more than one that implies it shows everything.

Two readers, two answers

Each check ends in one of three words: it passes, it fails because the files contradict each other or the chain, or it is unverified, meaning the files in the reader’s hands do not establish the row either way. Unverified is not a pass. A report can contain unverified rows without any check having failed.

Three columns. The third, the answer for the holder of the portable archive, comes last. If this table is wider than the space it has here, scroll it sideways to read it.

For each question about a published row, what a reader holding the seven flat files can establish and what a reader holding the portable archive can establish.
QuestionHolder of the seven flat filesHolder of the portable archive
The day a withdrawal row states, against the event it citesSettled where the set holds the cited event and its links run to it. Where the cap dropped the entry and no link corroborates it, unverified: not established, and not reported as damage.The check follows the pointer to data/changelog.jsonl and reads the event there. It passes where the chain agrees with the row and fails where the chain contradicts it.
The day a record joined the listThree flat files state it, and two disagreeing is damage. A day later than a confirmed addition the reader holds fails. A day moved earlier in all three is unverified.The record’s own events in the changelog state it, withheld readings included. A day the chain contradicts fails. Settled for every record whose addition the chain carries.
A record already listed when its source was first readCompared with a count. The baseline states how many records it counted. If the set puts more records than that opening on that day, the row fails. The same number, or fewer, is unverified: a count cannot tell one record from another, and a reader holding less of the list is not holding damage.Settled by the file the baseline read, where the archive carries it. The record’s name found in it passes; missing from a file that names the rest of that day’s records, it fails. Where the archive does not carry the file, or the names in it cannot be found, the flat-files answer stands.
Which company a record belongs to, and which authority published itThe files that name them are compared and fail outright where they differ. Not contradicted if every file is changed together.The same comparison, and the record’s own events too, for the authority and the country: a record cannot change either and stay the same record. The company’s name and identifier are not read off events.
The authority’s word, and the sentence it quotedThe files that state the word are compared and fail where they differ; a sentence that denies an approval beside the word accredited fails. The word and the sentence are also compared with the declarations in force over the record’s own period in the events the capped feed holds, and fail where they differ. Where the feed holds no declaration over that period the answer is unverified.The same comparison, over the whole changelog, which holds the events the capped feed does not: a record unverified from the feed can pass here. Still unverified where the changelog records no declaration over the period. What the authority wrote is settled on its own page, not by either reader.
Where the chain ends, and when anything was writtenNot settled by these files: whoever publishes the set writes the index and the stamp in one pass, and nothing in the set is dated against anything else.More securely, through the timestamp proof it carries, which is taken over bytes naming the index as published. Only once the proof is checked with ots verify; until then unverified.

The difference can be seen on one row. Take a set whose feed carries only some of the bodies, and move the day on a withdrawal row in the flat files while leaving the chain honest. A reader holding only the flat files has that row reported as unverified, and the report as a whole is not marked failed. A reader holding the archive has the check follow the pointer to data/changelog.jsonl, find the event the row cites, and fail the row. On the unaltered set neither reader is told anything is wrong: the archive reader’s row passes, and the flat-files reader’s stays unverified.

What the published files settle

For a reader holding the seven flat files, four things, from these files alone, without trusting this site or its operator. Each is a statement that files agree with one another or with the chain, which is less than a statement that the listing is right, and the bound of each is given with it.

What they do not settle

For that same reader, these are open or only partly settled, and each is bounded rather than hidden. The next two headings say which of them a reader holding the archive can close.

Runs of consecutive withheld entries in this set’s chain index, by length. The last entry in each run is corroborated by the entry published after it; the entries before it are not.
Run lengthRuns
13
71

This is a limit of what a windowed feed can show, not a defect in it: a feed that withheld nothing would be publishing provisional claims a second run has not yet confirmed. Where the exact position matters, the portable archive settles it. It carries the whole chain, not a window on it.

What a reader holding the portable archive settles in addition

The portable archive’s check does not stop at naming data/changelog.jsonl. It follows that pointer: it reads the changelog the archive carries and uses it in the check of each issued extract, where the flat-files reader’s report prints the pointer and leaves the lookup to the reader. Three things follow, each with its bound.

Two bounds apply to the first two, and the first of them to all three. First, the changelog is used only after the archive has walked it: if the chain check failed, or a line of the file cannot be read as an event, the changelog is set aside and each row is reported exactly as the flat-files reader would see it, because a body read out of a chain that does not walk could make a check pass. An archive built from the exported files alone carries no chain beyond the feed and gets the same flat-files answer. Second, a body found in the changelog still has to be reached by the set’s own links before a withdrawal row or a start day rests on it.

A fourth thing comes from the snapshots and not from the changelog. For a record already on the list when its source was first read, the archive reader looks for the record’s name in the file the baseline read, the one its snapshot_sha256 names, where the archive carries it. The name found there passes the row. The name missing from a file in which the names of the rest of that day’s records are found fails it, which settles a swap at the same count as well as an addition, because it reads the publisher’s own bytes and not a number. The search is for text, folded the way the ledger folds a company name to make its identifier, so a name could also be in a file for another reason.

What the archive reader still cannot settle

This page is information taken from official published lists. It is not tax, legal or professional advice, and it does not replace checking the official source.