Skip to main content

hiddenink

Inspect hidden Unicode and supported file metadata without overstating what was examined. Cleaning is conservative, local, and reported as separate removal, folding, and normalisation counts.

PyPI Python License

Apache-2.0 · Python 3.10+ · dependency-free core · offline operation

Install

pip install hiddenink

The default package has no runtime dependencies. The former c2pa and research extras were removed because this release did not call their dependencies; declaring unused functionality made the package boundary misleading.

Use

Inspect files:

hiddenink inspect notes.md
hiddenink inspect image.png --json
hiddenink inspect --recursive src/ --fail-on invisible

Clean text to standard output, preview changes, or replace a file:

hiddenink clean notes.md
hiddenink clean --check --recursive src/
hiddenink clean --dry-run image.png
hiddenink clean --in-place --backup notes.md

Directory traversal is opt-in with --recursive. Traversal is lexical and deterministic; duplicate files are processed once. .git, .hg, .svn, common cache/virtual-environment directories, node_modules, build, and dist are ignored. Symbolic links and non-regular files are refused rather than followed. Bytes that are neither a recognised container nor decodable by the UTF-8 text reader are reported as an input error. One operation accepts at most 10,000 files and 256 MiB in aggregate; text APIs accept at most 1,000,000 codepoints and reports retain at most 10,000 findings.

In-place cleaning reads and preflights every target before changing the first one. Each changed file is written to a same-directory temporary file, synced, given the original file's mode and timestamps, and atomically replaced where the platform supports os.replace. A pre-existing .bak is never overwritten unless --overwrite-backup is also supplied. Cross-file atomicity is not possible: a later, unexpected filesystem failure can still leave an earlier replacement complete, but never partially written.

Exit codes:

  • 0: operation completed and no requested threshold was exceeded.
  • 1: --check found a change or --fail-on found a matching severity.
  • 2: usage, I/O, unsupported-input, malformed-input, or refusal condition.

What inspection means

Every report includes a parse status, a coverage statement, warnings, and refusal reasons. “No findings” means only that no finding was observed inside that stated coverage.

Input Coverage
UTF-8 text Flagged Unicode codepoints plus heuristic mixed-script detection
PNG/JPEG Validated container structure and supported metadata chunks/segments
SVG Parsed XML metadata plus a Unicode scan of decoded markup/text
DOCX/XLSX/PPTX/ODF Document properties only
PDF Shallow lexical metadata scan

Office body text, Word comments/revisions, spreadsheet cells, presentation slides, and embedded media are not inspected. PDF compressed object streams, incremental-update semantics, encryption, and unsupported encodings are not a full-parser claim. These formats therefore report partial coverage rather than equating parser omission with absence.

The human report escapes C0/C1, ANSI/OSC, and bidirectional terminal controls from filenames and metadata. JSON remains machine-readable and preserves the original values through JSON escaping.

Cleaning policy

hiddenink distinguishes detection from rewriting. The profiles are:

  • prose: remove policy-defined hidden controls and fold exotic spaces while preserving normal typography.
  • code: additionally fold selected typography. Mixed-script/confusable text is reported; it is not automatically rewritten merely because it appears in a source file, since strings and comments are not parsed by language syntax.
  • data: apply the code policy, drop a leading BOM, and normalise CRLF to LF.

Context-dependent Unicode is preserved only when a supported sequence rule applies. Registered variation sequences, emoji sequences, and orthographic joiners are content, not generic “invisible junk.” URL and Markdown handling is heuristic; it is not a claim of complete URI or CommonMark parsing. Review a --dry-run report before applying policy-driven changes to valuable text.

Binary cleaning is narrower than metadata inspection. A cleaner may refuse a malformed file, a structure it cannot validate, or a file whose provenance could be invalidated. It does not treat EXIF, XMP, ICC profiles, rights data, or arbitrary text chunks as interchangeable. Preserve the original and use an independent decoder when fidelity matters.

C2PA boundary

The core can identify some container structures that may carry JUMBF/C2PA bytes. That is not the same as parsing a manifest or validating a credential. Reports distinguish:

  • C2PA-looking container bytes;
  • a structurally recognised manifest store;
  • retained manifest bytes;
  • parsed manifest claims; and
  • cryptographic validation of the credential and hard binding.

The dependency-free core does not parse manifest claims or perform the final cryptographic credential/hard-binding validation. It never calls retained bytes “valid provenance.” C2PA defines hard bindings as cryptographic bindings between a manifest and an asset, and defines soft bindings separately; see the official C2PA Content Credentials specification. Because rewriting unrelated asset bytes can invalidate a hard binding, the safe outcome may be refusal.

Statistical watermark boundary

hiddenink has no vendor detector and no model-specific statistical watermark scheme. Text reports therefore say that this layer was not evaluated; binary metadata reports do not repeat an irrelevant text-watermark notice.

This project does not assert that Claude inserts zero-width characters, that EXIF/XMP proves Claude authorship, or that C2PA proves AI generation. Anthropic's current official Transparency Hub describes watermarking as an area it continues to explore; that source does not support the rollout story previously published here.

Law and policy

Article 50(2) of the EU AI Act places machine-readable marking obligations on providers of covered AI systems, subject to feasibility and stated exceptions. Article 50(4) separately addresses disclosure by deployers for deepfakes and certain public-interest text. The Regulation applies from 2 August 2026, with the staged exceptions in Article 113. Read the official EUR-Lex text of Regulation (EU) 2024/1689. Nothing in this README is legal advice, and the project does not infer a user's obligations from a file alone.

Conformance corpus

python -m hiddenink.audit runs a project-authored Unicode regression corpus. It is useful for repeatable development tests, not proof of universal correctness or market leadership. Policy cases are unscored. A comparison is publishable only with the competitor repository, exact revision, command and flags, run date, runtime environment, and independently reviewable cases.

See RESULTS.md for the current self-run and its limitations. The author writes both hiddenink and the corpus; that conflict of interest is not eliminated by a passing score.

Security and responsible use

Read SECURITY.md for resource limits, hostile-file assumptions, and vulnerability reporting. If a document has been used in an authorship or academic-integrity dispute, preserve the original before inspecting it and see docs/FALSE-FLAG.md.

License

Apache-2.0. See LICENSE.

Not affiliated with or endorsed by Anthropic, C2PA, or the European Union.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

hiddenink-0.2.1.tar.gz (404.9 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

hiddenink-0.2.1-py3-none-any.whl (79.3 kB view details)

Uploaded Python 3

File details

Details for the file hiddenink-0.2.1.tar.gz.

File metadata

  • Download URL: hiddenink-0.2.1.tar.gz
  • Upload date:
  • Size: 404.9 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for hiddenink-0.2.1.tar.gz
Algorithm Hash digest
SHA256 7e37d21e47dd06a8ecf9eb89e8a5f5f4f5291d0daec335bdfcde988a13193fa0
MD5 c15ee504ddb581ba1b9bf42a62b62ba3
BLAKE2b-256 0132f78897a1ffabd92b9ea146909cef80a69cbc4561fa55ddbf25232809ece3

See more details on using hashes here.

Provenance

The following attestation bundles were made for hiddenink-0.2.1.tar.gz:

Publisher: release.yml on syahra712/hiddenink

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file hiddenink-0.2.1-py3-none-any.whl.

File metadata

  • Download URL: hiddenink-0.2.1-py3-none-any.whl
  • Upload date:
  • Size: 79.3 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for hiddenink-0.2.1-py3-none-any.whl
Algorithm Hash digest
SHA256 62327fbd7cf01f9ab8b3baf6b0f726a167ed76255c4e72d8416958430a5f5c5b
MD5 54acdb9eb03cb0b898cee008df80b6cd
BLAKE2b-256 286ccb5a6b74e05cc68091c2d5d3dc8603c0d0e352ab8db1442812016203b08e

See more details on using hashes here.

Provenance

The following attestation bundles were made for hiddenink-0.2.1-py3-none-any.whl:

Publisher: release.yml on syahra712/hiddenink

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

This release

0.2.1 This release

2 files

0.1.2

2 files

0.1.1

2 files

0.1.0

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page