Files
camoufox/pythonlib/tests/test_shipped_data.py
T
Jake WriterandClaude Opus 5.5 9a42b6a17f chore(python)!: drop data the package never draws from
voices.json shipped in the wheel, but no code in the package reads it: the
voice draw uses voice-manifests.json and voice-uris.json. Its only readers
are the TypeScript port's golden-fixture generator and data-sync script
(typescript/scripts/golden/identity_golden.py,
typescript/scripts/sync-identity-data.py), which live on another branch and
will need a new source; the last copy is at
676fb3f:pythonlib/camoufox/voices.json. docs/per-context-patches.md
described it as runtime data and now describes the files that are.

webgl_data.db held two rows with zero weight on every OS ("Intel(R) HD
Graphics 400, or similar" from "Intel Inc." and "Radeon R9 200 Series, or
similar" from "ATI Technologies Inc."), left behind when their impossible
macOS weights were zeroed. No draw can reach them. They are deleted with
secure_delete so their blobs do not linger in free pages; the file is not
vacuumed, so the other pages are unchanged. A new test requires every row
to be drawable on at least one OS.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-25 20:34:17 -06:00

97 lines
3.7 KiB
Python

"""The data files that ship must not contain an identity we would refuse to use.
`camoufox.coherence` filters at draw time, so an impossible row can never reach
a page either way. This is the second filter, on the data itself: a row that
survives here is one a future refresh could ship, a consumer reading the JSON
directly would get, and a reviewer would take as real. Both filters run the same
rules -- `scripts/clean-fingerprint-data.py --write` is what makes these pass.
Dropped on 2026-09-17: 38 of 435 presets (26 with a GPU their OS cannot report,
7 pairing Apple Silicon with a core count Apple never shipped, 4 with a colour
depth their GPU contradicts, 3 with a phone viewport, 1 claiming 40 touch
points), and 2 impossible macOS weights in webgl_data.db.
"""
import json
import sqlite3
import sys
from os.path import dirname, join
from pathlib import Path
import pytest
sys.path.insert(0, join(dirname(__file__), ".."))
from camoufox import coherence # noqa: E402
from camoufox.fingerprints import from_preset # noqa: E402
from camoufox.webgl.sample import DB_PATH # noqa: E402
DATA = Path(__file__).parent.parent / "camoufox"
PRESET_FILES = ("fingerprint-presets.json", "fingerprint-presets-v150.json")
OS_KEY = {"macos": "mac", "windows": "win", "linux": "lin"}
@pytest.mark.parametrize("filename", PRESET_FILES)
def test_every_bundled_preset_is_coherent_as_stored(filename):
presets = json.loads((DATA / filename).read_text())["presets"]
for os_name, entries in presets.items():
assert entries, f"{filename}/{os_name} has no presets left"
for index, preset in enumerate(entries):
config = from_preset(preset, "152")
violations = coherence.validate(config, OS_KEY[os_name])
assert violations == [], (
f"{filename} {os_name}[{index}]: "
+ "; ".join(v.detail for v in violations)
+ " -- run scripts/clean-fingerprint-data.py --write"
)
def test_no_gpu_is_offered_to_an_os_that_cannot_report_it():
connection = sqlite3.connect(DB_PATH)
try:
rows = connection.execute(
"SELECT vendor, renderer, win, mac, lin FROM webgl_fingerprints"
).fetchall()
finally:
connection.close()
assert rows, "webgl_data.db is empty"
for vendor, renderer, *weights in rows:
for os_key, weight in zip(("win", "mac", "lin"), weights):
if weight and weight > 0:
assert coherence.gpu_fits_os(renderer, os_key), (
f"{renderer!r} is offered to {os_key} at {weight}"
)
def test_each_os_still_has_gpus_to_draw_from():
"""The filter must not empty a pool -- a single GPU per OS is its own tell."""
connection = sqlite3.connect(DB_PATH)
try:
for os_key in ("win", "mac", "lin"):
count = connection.execute(
f"SELECT COUNT(*) FROM webgl_fingerprints WHERE {os_key} > 0" # nosec
).fetchone()[0]
assert count >= 2, f"{os_key} has {count} GPU(s) left"
finally:
connection.close()
def test_every_gpu_row_can_be_drawn_on_some_os():
"""A row no OS can draw is dead weight a reader would take as real data."""
connection = sqlite3.connect(DB_PATH)
try:
rows = connection.execute(
"SELECT vendor, renderer, win, mac, lin FROM webgl_fingerprints"
).fetchall()
finally:
connection.close()
undrawable = [
(vendor, renderer)
for vendor, renderer, *weights in rows
if not any(
weight > 0 and coherence.gpu_fits_os(renderer, os_key)
for os_key, weight in zip(("win", "mac", "lin"), weights)
)
]
assert undrawable == []