Repository navigation
Read the newer EMI line, test the parser in the canary, validate numeric flags - #11
Merged
Merged
Conversation
…ric flags - The EMI figure is read whether or not the site prints "/m", and the "Save extra ... on" promotion beside it is no longer taken for the tag; before this, the newer card shape gave no EMI and put "EMI 15,916" in the hub column (canary runs of 2026-10-08, -10 and -15). - The canary asserts parser invariants instead of an EMI share and a strike/discount pairing, its checks live in .github/canary_check.py, and exit 5 (content never obtained) now fails instead of warning. - --pages, --concurrency, --proxy-block-retries, --delay and --retry-delay reject out-of-range values with exit 2 in all three engines (--retry-delay -1 used to crash the first retry); scraper_api_client.py validates --timeout, --retries and --retry-delay. - The credential scan compares excluded names relative to the repo root, fails when it scanned nothing, and reads .env backups, JSON, CSV, HTML and page dumps. - Root HTML dumps, NAME.pageN dumps and live/out/tmp-style directories are gitignored. - Playwright and pyppeteer pass the navigation's HTTP status to the classifier. - Comments and docs state rules in place instead of citing private notes by section; a suite guard keeps it that way. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
jehrr
marked this pull request as ready for review
October 15, 2026 13:53
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes from the 2026-10-14 audit of
af36221, plus the canary rule that a run which did not test the site must not end green.Problems and resulting behaviour
1. EMI missed, EMI line read as the hub (parser defect behind the red canary). The audit could not tell whether the red canary on 2026-10-08/09/10 came from the site or the parser. The artefacts of 2026-10-08, -10 and -15 settle it. The cards there print
EMI 15,916(no/m) next to a newSave extra ₹19.5K onpromotion. The 2026-10-14 artefact still hasEMI 18,833/m *._EMI_RErequired/m, which had two effects:EMI 15,916contains a comma, so it became thehubon 82–102 rows a run.Now both wordings are read, the promotion is recognised and not left over as the
tag, and a fixture cut from the 2026-10-15 canary dump pins the values. The trimmed fixture was verified to parse identically to the untrimmed card.Re-parsing the four downloaded dumps (2026-10-08, 10-10, 10-14, 10-15) with this branch reads an EMI on 60/60, 102/102, 82/82 and 94/95 rows (by artefact date), with 0 EMI lines in the hub.
2. Canary (owner rule, section 12).
Before: red 3 of 8 days on an
emi_monthly ≥ 90%floor and on "strike price always travels with the discount badge". On 2026-10-10 the site printed 20 strike prices with no badge, which is a merchandising choice. Exit 5 ended green with a::warning::, even though a runner-side navigation timeout also exits 5.After: the assertions moved to
.github/canary_check.py(runnable against an artefact and exercised by the offline suite). They test the parser:The EMI share and the strike share are printed, not asserted. Exit 3/4/5/6/2/1 all fail with
::error::.Run against the old rows of the three red days, the new check fails each one by name: "N row(s) carry EMI-box text in another column". Against the same dumps re-parsed by this branch, it passes all four.
No secret is needed: the canary runs from a bare runner.
SPINNY_CDP_ENDPOINTstays optional and env-only.3.
--retry-delay -1crash and other numeric flags.page_flowvalidators and fail with exit 2 naming the flag:--pagesand--concurrency(≥1),--proxy-block-retries,--delayand--retry-delay(≥0).--retrieswas already validated and is kept.scraper_api_client.pynow validates--timeout(≥1),--retries(≥0, extra attempts) and--retry-delay(≥0).4. Credential scan.
path.relative_to(REPO).parts. Before, a clone under anyvenv/parent scanned 0 files and printed ok..env*backups,.json,.csv,.htmlandNAME.pageNdumps are read too.pyvenv.cfgdirectories are still skipped.5.
.gitignore. Now covers root/*.html,*.page[0-9]*, andlive/ out/ output/ runs/ results/ tmp/ scratch/ dumps/.check-ignoreconfirms that workflows, tests, samples,.env.exampleandsmoke_test.pystay tracked.6. HTTP status to the classifier. Playwright and pyppeteer pass the
goto()response status. The status is reset after a solve navigates the page, and a non-int status is treated as unknown. Selenium has no status and keeps the page's own 404 copy.7. Private citations.
§Nand theCLAUDE.md/ "family notes" mentions from tracked files; the rule is stated in place.8. Wording.
run_metadocstring no longer describes aproductmode and asoldcolumn.Evidence
pip checkis clean.pytest -qpasses.PYTHONDONTWRITEBYTECODE=1and__pycache__cleared between runs; the restored tree is green. The faults planted:.envbackups unread;§reinserted;--delay type=float;--retry-delayminimum −9;/mrequired again;venv/parent: 37 files scanned. A planted.env.bakkey was found.scraper_api_client.py --retries -1giveserror: argument --retries: --retries must be at least 0, not -1.Not changed
[Unreleased]carries the changes, led by behaviour-change blockquotes.captcha_solver.py,product_parser.py) describe where a lesson came from and have no code effect.🤖 Generated with Claude Code