Skip to content

Scraper API: send waitFor as an object, read the target status from http_code - #19

Merged
jehrr merged 1 commit into
mainfrom
fix/scraper-api-waitfor-object
Sep 23, 2026
Merged

jehrr merged 1 commit into
mainfrom
fix/scraper-api-waitfor-object

Conversation

@jehrr

@jehrr jehrr commented Sep 23, 2026 •

Copy link
Copy Markdown
Collaborator

Two defects in scraper_api_client.py

Measured 2026-09-23 against https://scraper.2captcha.com/tasks/sync:

  1. waitFor sent as a JSON-encoded string (what _build_wait_for returned) is answered HTTP 422 ScrapeParser: params.waitFor must be an object — and the call is still billed ($0.0005). The same request with an object answers 200. So every run with --wait-text / --wait-element / --wait-state failed with exit 5 and cost money. _build_wait_for now returns a dict (logged through json.dumps), and the docstring that said the API wanted a double-encoded string now says what was measured.
  2. The target status was read from status, which is the API's own verdict string ("success"). The target site's HTTP code is http_code. This client LOGS that value (it does not classify on it), so a target 403/503 read "success" in the log. It now reads http_code (int), falling back to status only if that is itself an int.

Regression check

test_scraper_api_sends_waitfor_as_an_object_and_reads_http_code in smoke_test.py: drives the real function with requests.post stubbed (no network), returning {"status":"success","http_code":403,"body":"<html></html>"}, and asserts (a) the payload's waitFor is a dict and (b) the status it reads is 403 (int).

Control: (registered with ok &= … in main()) with origin/main's scraper_api_client.py swapped into this branch's tree (file hash confirmed changed), the suite went red with exactly 2 failures, both this check's messages (waitFor came back as the string '{"text": "results"}', the logged status as ['success']). Restored: smoke_test: OK. This client's fetch_html returns only the HTML and LOGS the status, so part (b) asserts on the captured log record rather than a return value.

Live result

One call, key from the environment: scraper_api_client.py --url 'https://www.amazon.com/s?k=wireless+headphones' --wait-text results → API HTTP 200 (no 422), log Upstream page HTTP status 200, 16 rows, exit 0, sidecar status complete.

Not changed

Unlike its siblings, this client does not hand the target status to a page classifier at all — it only logs it — and this PR does not change that (it would be a behaviour change beyond this fix; worth its own PR). The module docstring's API-surface block now shows the object form and the real response shape. The browser engines and product_parser.py are untouched. No version bump — the CHANGELOG entry is under [Unreleased]. Reference fix: zimmo-scraper PR #1.

🤖 Generated with Claude Code

…ttp_code

Measured 2026-09-23 against the live /tasks/sync endpoint: waitFor sent
as a JSON-encoded string is answered HTTP 422 "params.waitFor must be an
object" and still billed ($0.0005); as an object it is answered 200.
The response's `status` is the API's own verdict ("success"); the
target's HTTP code is `http_code`, which is now what reaches the page
classifier (fallback to `status` only when it is an int).

Adds one offline regression check, controlled: with the old client the
suite goes red on exactly that check.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@jehrr
jehrr merged commit 4ca7027 into main Sep 23, 2026
7 checks passed
@jehrr
jehrr deleted the fix/scraper-api-waitfor-object branch September 23, 2026 15:30
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant