Skip to content

Releases: SybilGambleyyu/pdffence

PDFFence 1.27.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 12:29

Private batch mappings now detect accidental source reuse

PDFFence 1.27.0 adds require_unique_document_sources (PFP017), a
high-severity, batch-only policy gate enabled by pdffence init.

It detects when an exact private relative manifest path is assigned to more
than one public review ID on the same before or after side. Each affected ID
receives a generic finding containing only the side and number of references;
the report never reveals the root, path, filename, source value, hash, or PDF
material.

The gate is deliberately narrow. It does not compare contents, infer renames,
or treat hard links and other filesystem aliases as identity. Disable it
explicitly only for a reviewed one-to-many workflow.

Exact repeated same-side sources also share one validated snapshot per batch
run, avoiding repeated parser work from duplicate manifest entries.

Validation included 277 tests, Ruff, bytecode compilation, a 161-entry
PDFCAB-derived batch, an adversarial duplicate-source manifest, reproducible
fixed-timestamp wheel/source builds, fresh Python 3.12/3.13 installs, Twine,
and a dependency audit. See docs/validation.md for scope and limitations.

Install the tagged wheel:

python -m pip install https://github.com/SybilGambleyyu/pdffence/releases/download/v1.27.0/pdffence-1.27.0-py3-none-any.whl

PDFFence is structural, local review tooling. It does not render PDFs, compare
visual appearance, validate PDF conformance or signatures, decrypt sources,
extract text, execute actions, follow URIs, or detect malware.

PDFFence 1.26.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 12:09

PDFFence 1.26.0 makes the privacy-safe batch workflow practical for large, same-layout handoffs.

  • New pdffence batch-init BEFORE_ROOT AFTER_ROOT MANIFEST recursively generates a private manifest with deterministic opaque IDs.
  • It pairs only identical relative PDF paths. Unmatched paths stay explicit additions/removals; it never guesses a rename.
  • The generator requires an explicit output path, writes atomically, and never prints the private manifest. It rejects symbolic links, non-regular PDF-named entries, invalid paths, cycles, oversized scans, and manifests beyond normal limits.

The release passed 273 automated tests and a generated-manifest run over all 161 PDFCAB pairs. Every generator-routed public report exactly matched its standalone pdffence diff result. Fixed-timestamp wheel and source builds were byte-identical and passed Twine checks; fresh Python 3.12/3.13 installs passed the 161-document workflow. A clean dependency audit found no known vulnerabilities.

Install the wheel directly:

python -m pip install https://github.com/SybilGambleyyu/pdffence/releases/download/v1.26.0/pdffence-1.26.0-py3-none-any.whl

PDFFence 1.25.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 11:48

PDFFence 1.25.0 adds a privacy-safe manifest batch workflow for serious PDF handoffs and release review.

  • pdffence batch compares explicitly paired PDFs from private before/after roots, including renamed, added, and removed documents.
  • Reports never expose manifest paths or roots. Each result uses a caller-chosen, deliberately public opaque ID; JSON, Markdown, and SARIF are supported.
  • New require_same_document_set (PFP016) is a high-severity, batch-only CI gate and is enabled by pdffence init.
  • Manifests are strict bounded JSON, reject unsafe paths and symbolic links, and batch execution is all-or-nothing.

The release was tested with 269 automated tests and an opaque-ID batch of all 161 PDFCAB pairs. Every batch entry exactly matched its standalone public diff result. Fixed-timestamp wheel and source builds were byte-identical and passed Twine checks; fresh Python 3.12/3.13 installations passed the corpus run.

Install the wheel directly:

python -m pip install https://github.com/SybilGambleyyu/pdffence/releases/download/v1.25.0/pdffence-1.25.0-py3-none-any.whl

PDFFence 1.24.1

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 11:24

Corrects the public installation instructions. PDFFence is currently distributed through checksummed GitHub Release artifacts; the former bare PyPI command did not resolve to a published package.

No analyzer behavior changed from 1.24.0.

PDFFence 1.24.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 11:12

Adds PFP015 (require_terminal_revision_footer) and a privacy-safe terminal revision-footer status. It rejects unlinked physical tails independently of PFP006 while allowing valid linked incremental updates.

Validated with 264 tests and the PDFCAB 1.24 process-bound score (161/161). Artifacts are fixed-timestamp reproducible and checksummed.

PDFFence 1.23.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 10:32

Terminal-footer evidence hardening

Own-revision ByteRange evidence now requires the final linked %%EOF footer to end the physical source, apart from its optional EOL. Raw bytes appended after that footer fail closed for PFP013 and PFP014 positive evidence.

This is a static layout review boundary, not cryptographic signature, certificate, trust, transform, or permission validation.

Validation

  • 260 source tests, Ruff, and bytecode compilation passed.
  • PDFCAB 1.23 scored 160/160 through the public CLI.
  • Fixed-timestamp wheel and source archive builds were byte-identical; Twine checks passed.
  • Fresh Python 3.12/3.13 wheel installs and Python 3.12 source-archive installs passed pip check, fixture verification, and the complete score.

See SHA256SUMS for release-asset hashes.

PDFFence 1.22.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 10:03

PFP014 adds a fail-closed historical signature boundary: every semantic ByteRange must omit exactly its direct hexadecimal /Contents token and end at the footer of that signature's own revision.

This permits correctly bounded historical signatures after later incremental updates while remaining distinct from current-file (PFP011) and endpoint-only own-revision (PFP013) evidence.

Validation: 256 tests, Ruff, pyHanko compatibility checks, reproducible wheel/sdist builds, and PDFCAB 159/159 process-bound scoring.

PDFFence 1.21.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 09:22

Signature ByteRange own-revision coverage

Adds PFP013, require_signature_byte_range_own_revision_coverage.

The new static review gate requires every semantic signature /ByteRange to end at the unambiguous footer of the revision containing its xref-addressable signature dictionary. It is intentionally distinct from current-file coverage: an older signature can remain correctly bounded after later incremental updates.

The release retains aggregate-only public output and fails closed for unavailable, ambiguous, malformed, direct, compressed, or over-limit revision evidence. It does not validate a signature, digest, certificate, trust chain, transform, permission, or incremental update.

Validation: 254 tests, Ruff, exact 158/158 PDFCAB process-bound score, a two-signature pyHanko interoperability exercise, reproducible wheel/sdist builds, and fresh Python 3.12/3.13 installation checks. See docs/validation.md for details.

PDFFence 1.20.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 08:38

PFP012: direct ByteRange signature values

  • Adds aggregate evidence for semantic signature dictionaries with /ByteRange whose top-level values are all direct PDF objects.
  • Adds the opt-in require_direct_byte_range_signature_values policy rule (PFP012).
  • Adds an isolated regression that retains a current, exact direct /Contents boundary while making one top-level signature value indirect.

This is a static object-layout review gate, not signature, digest, certificate, trust, transform, or permission validation.

Validation: 248 tests, Ruff, reproducible wheel/source builds, clean Python 3.12/3.13 wheel and Python 3.12 source-archive installs, and PDFCAB 1.20 scores of 157/157.

SHA-256

  • pdffence-1.20.0-py3-none-any.whl: edb13e9afff47b8f129d230caedd744e7a2b7bebedd54919fed3e5deb9306c35
  • pdffence-1.20.0.tar.gz: e705f212479d9dc8dfc4613a6d174d237b54951235dd6dcee6bf6fbc6647da4b

PDFFence 1.19.0

Choose a tag to compare

@SybilGambleyyu SybilGambleyyu released this 07 Aug 07:55

Adds an opt-in Contents-bound signature coverage gate (PFP011). It requires aggregate evidence that a semantic signature’s two-pair current-file ByteRange gap exactly matches a direct hexadecimal /Contents token, without exposing offsets or signature material.

Validation: 245 tests, Ruff, reproducible wheel and source builds, Twine checks, clean Python 3.12/3.13 installs, and 156/156 PDFCAB fixtures.