Repository navigation
Releases
Releases · antonsoo/fieldproof
fieldproof 0.2.7
pip install fieldproofCompatibility
- Python 3.13 and 3.14 are tested and declared. CI runs the suite on 3.14 as well, and the package's classifiers list both versions. The code is unchanged: with the newest release of every dependency, the tests pass on 3.14 and on 3.15's release candidate.
fieldproof 0.2.6
pip install fieldproofAccessibility
- The review UI, checked with axe-core (WCAG 2.1 A and AA, and its best-practice rules) in light and dark, at desktop and phone widths, on each sample document: no findings now. The faint text was 2.6:1 to 3.1:1 (light) and 3.4:1 (dark), and the "review" and "verified" labels just under 4.5:1 on their tints. The page has an
h1, and the page viewer, which scrolls, can take keyboard focus.
fieldproof 0.2.5
pip install fieldproofSecurity
- The review UI carries a Content-Security-Policy. Scripts, styles and fonts load from the server that served the page only, and
connect-src 'self'has the browser refuse to send a document, or anything read from it, to any other host, even for a script injected through a bug in how a field is rendered. Inline event handlers andevalare not allowed. Checked in Chromium and Firefox with a listener for policy violations, on the demo and onfieldproof servethrough an upload, an extraction and the page images: none.
fieldproof 0.2.4
pip install fieldproofChanged
- The review UI's fonts ship in the package.
fieldproof serveruns on your own machine, over documents you may not be free to share, and its page asked Google Fonts for its typography on every load (and fell back to system fonts without a connection). The same font files are now part of the wheel, with their SIL Open Font License texts (web/src/fonts/), and the page makes no request to any host but the server it came from. Nothing looks different: screenshots before and after match. The wheel grows from about 60 KB to about 530 KB.
fieldproof 0.2.3
pip install fieldproofSecurity
- The oldest dependency versions the package accepted had published advisories in exactly the code that reads what a stranger uploads:
python-multipart0.0.9,starlette0.38.6 (throughfastapi0.115),pdfminer.six20231228 (throughpdfplumber0.11.0) andPillow10.4 (theocrextra), plusclick8.1.8. An ordinary install already got current versions; an install held back by another package's constraints could get those. The minimums are now the first releases without an advisory:python-multipart>=0.0.31,starlette>=1.3.1,pdfminer.six>=20251230,click>=8.3.3,Pillow>=12.3, and with themfastapi>=0.133,pdfplumber>=0.11.9,typer>=0.16.pip-auditreports nothing for the locked versions or for the minimum ones, and the tests pass on both.
fieldproof 0.2.2
pip install fieldproofFixed
- A result or fixture JSON saved by a Windows editor or shell. Notepad's "UTF-8 with BOM" and PowerShell's
-Encoding utf8put a byte-order mark first ("not valid JSON (line 1, column 1: Unexpected UTF-8 BOM ...)"), and PowerShell's>writes UTF-16 ("is not UTF-8 text"). All three are read, by the CLI and by the review server. - Output written to a pipe or a file is UTF-8, so a document path outside the system's code page can be printed when stdout is redirected on Windows.
fieldproof 0.2.1
pip install fieldproofAdded
- Published to PyPI:
pip install fieldproof. The package includes the built review UI, sofieldproof serveworks without a Node toolchain (scripts/bundle_ui.pybuilds it into the package before a release). fieldproof --version.
Fixed
- A value quoted from inside a longer word could be marked
verified. The exact matcher refused a quote that cuts a word, and the fuzzy fallback then scored the same fragment 100/100 as a perfect partial match. On the example invoice, a vendor name ofwind(inside "Northwind") and an invoice number of0214(inside "NW-20260214") both verified. A match now has to cover whole words; when the best fuzzy window cuts one, the quote is scored against the whole words, so those two areunsupportedand458.00is a weak match for$2,458.00. Punctuation glued to a word may be left out of a quote (1for1,,2,458.00for$2,458.00), and every such occurrence counts when deciding whether a quote is ambiguous. - A string value one digit off verified:
NW-20260215for a document readingNW-20260214is 96% similar, which passed both the grounding and the value check. Every run of digits in a string value now has to appear in the evidence as written. --provider anthropicagainst the real SDK. The provider had only met a mocked client, which returnedparsed_output=Nonefor a reply that isn't the schema. The SDK'smessages.parseraises instead: an extraction cut off atmax_tokens(a long invoice) or refused came out as a pydantic traceback,Invalid JSON: EOF while parsing a string. The provider now streams the reply, reads itsstop_reasonand says which it was in one line:error: Claude's reply was cut off at 16000 output tokens, before the Invoice was complete; raise the limit (--max-tokens) or extract a shorter document. New--max-tokensoption. The tests run the real SDK over a mocked HTTP transport.- The declared minimum
anthropic>=0.40had nomessages.parse:AttributeError: 'Messages' object has no attribute 'parse'. The minimum is 0.77, the first release with structured outputs on the Messages API, and the provider tests pass on it. - Two more declared minimums did not work. With
typerbelow 0.15.4 every command stopped (Type not yet supported: pathlib.Path | Noneon 0.12.0;make_metavar() takes 1 positional argumenton--helpwith a current click), and withpydanticbelow 2.10 a typed result could not be built fromEvidencedvalues. The minimums aretyper>=0.15.4andpydantic>=2.10, and CI has a job that installs the oldest allowed version of every direct dependency on the oldest supported Python and runs the tests there. - A match could begin or end inside a ligature (
inalmatched "final"). - A result or fixture file that isn't valid JSON, isn't an object, or doesn't fit the schema printed a traceback from
extractandverify, and was an unexplained 500 in the review UI. The CLI prints one line (error: result.json does not match the Invoice schema: total.value: Input should be a valid number, unable to parse string as a number) and the server answers 422 with the same message. A file that isn't a PDF, a missing API key and a failed API request are one line too.
Added
- Seeded fuzz tests for the promise above: an exact match always covers whole words, a piece of a longer word never verifies, a value with a number the document lacks never verifies, and a damaged result file ends in a report or a one-line error.