使用 cURL 生成 Kasada 请求头

作者:solvethree阅读需 1 分钟

创建 KasadaTask,等待状态变为 ready,然后通过同一个代理,使用返回的浏览器身份发送整个 solution.headers 对象。独立 Kasada 目前支持 www.ticketmaster.com 上的 HTTPS 目标。

本页内容

使用 cURL 创建、轮询并提交

此脚本需要 Bash、cURL 7.76 或更高版本、jq 和 openssl。将 SOLVETHREE_API_KEY 设置为工作区 API 密钥,将 SOLVETHREE_PROXY 设置为 HTTP 或 HTTPS 代理 URL。将 API 密钥保留在服务端,并关闭 shell 跟踪。

此示例全程使用同一个代理。Kasada 请求必须包含 type、url,并且必须且只能提供 proxy 或 proxyCandidates 中的一项;不得包含 site 或 action 等 reCAPTCHA 字段、session 或自定义浏览器身份字段。请参阅 Kasada 请求规范。

KASADA · 创建、轮询并应用结果
#!/usr/bin/env bash
set -euo pipefail
: "${SOLVETHREE_API_KEY:?Set the API key}" "${SOLVETHREE_PROXY:?Set the proxy}"
# Requires bash, curl, jq and openssl. Do not enable shell tracing.
work=$(mktemp -d)
chmod 700 "$work"
trap 'rm -rf "$work"' EXIT
request_id=$(openssl rand -hex 16)
printf 'Recovery requestId=%s\n' "$request_id"
printf 'Authorization: Bearer %s\n' "$SOLVETHREE_API_KEY" > "$work/auth"
jq -n --arg proxy "$SOLVETHREE_PROXY" --arg id "$request_id" '{"type":"KasadaTask","url":"https://www.ticketmaster.com/","proxy":$proxy,"requestId":$id}' > "$work/input.json"
api='https://api.solvethree.com/v1'
curl --fail-with-body --silent --show-error --max-time 30 \
  --header @"$work/auth" --header 'Content-Type: application/json' \
  --data-binary @"$work/input.json" --output "$work/result.json" "$api/tasks?waitMs=0"
task_id=$(jq -er '.id' "$work/result.json")
encoded_id=$(jq -nr --arg id "$task_id" '$id|@uri')
printf 'Recovery taskId=%s\n' "$task_id"
deadline=$((SECONDS + 180))
while [[ $(jq -r '.status' "$work/result.json") =~ ^(pending|solving)$ ]]; do
  remaining=$((deadline - SECONDS))
  (( remaining > 0 )) || { echo 'Local deadline reached; resume the saved task ID' >&2; exit 1; }
  timeout=$((remaining < 25 ? remaining : 25))
  curl --fail-with-body --silent --show-error --max-time "$timeout" \
    --header @"$work/auth" --output "$work/result.json" "$api/tasks/$encoded_id?waitMs=15000"
  [[ $(jq -r '.status' "$work/result.json") =~ ^(pending|solving)$ ]] && sleep 1 || true
done
[[ $(jq -r '.status' "$work/result.json") == ready ]] || { echo 'Solver task failed' >&2; exit 1; }
user_agent=$(jq -er '.solution.userAgent' "$work/result.json")
client_hints=$(jq -er '.solution.secChUa' "$work/result.json")
jq -r '.solution.headers | to_entries[] | "\(.key): \(.value)"' "$work/result.json" > "$work/target-headers"
curl --silent --show-error --max-time 30 --proxy "$SOLVETHREE_PROXY" \
  --header @"$work/target-headers" --user-agent "$user_agent" \
  --header "sec-ch-ua: $client_hints" --output "$work/target-response" \
  --write-out 'Target HTTP %{http_code}\n' 'https://www.ticketmaster.com/'
# Inspect the application's response before treating the operation as successful.
# Replace the example target path with the actual supported workflow URL.

将任务体和最终 cURL 调用中的示例目标 URL 都替换为你要使用的受支持工作流 URL。不要针对一个 URL 求解,却将结果提交到无关目标。

脚本通过 Bearer 请求头进行身份验证,创建一个任务,并仅轮询返回的任务 ID。创建请求的超时时间为 30 秒;轮询设置了 180 秒的本地截止时间,并限制 GET 请求的执行时间。这些是脚本限制,并非求解时间保证。脚本未启用自动重试或重定向跟随。

应用整个请求头对象

pending 和 solving 表示应继续轮询。只有 ready 状态才包含可用的求解结果。脚本使用 jq 读取原始 solution.headers 对象,并将每个条目转换为请求头文件中的一行;它不会只选取某个请求头,也不会将任务 ID 当作求解结果。

最终请求会加载该请求头文件,设置 solution.userAgent 和 solution.secChUa,并使用原来的代理。请配套使用这些值,不要替换成你平常使用的浏览器请求头。

API 响应、生成的请求头和目标响应都保存在私有临时目录中,不会输出。不要将它们写入常规日志,也不要启用 shell 跟踪。

恢复任务,而不是创建新任务

保存输出的恢复 ID。重新运行脚本会生成新的 requestId,并不属于恢复尝试。要恢复创建操作,请使用保存的请求 ID 和完全相同的原始任务输入。脚本会在退出时删除输入文件,因此如果需要重建请求,请安全地保留这些输入。

POST 请求在返回任务 ID 前超时。

连接超时并不能证明任务创建失败。

试试这样做: 使用保存的 requestId 提交同一个任务请求。相同的输入会恢复现有任务;复用该 ID 时更改输入会产生冲突。

已到达本地轮询截止时间。

使用输出的任务 ID,检查现有任务是否仍处于待处理或求解中状态。

试试这样做: 为该 ID 设置新的有限截止时间,恢复 GET 轮询。不要仅仅因为本地等待结束就创建替代任务。

API 请求返回非成功 HTTP 响应。

API 调用使用 --fail-with-body,因此 cURL 会在脚本读取成功响应载荷前退出。

试试这样做: 为便于诊断,请添加 HTTP 错误处理程序,在清理前以非公开方式检查已保存的响应体。请修正报告的请求问题,不要使用未更改的输入盲目重试。

任务进入 failed 状态。

示例会输出通用失败消息;响应中还包含 errorCode 和 error。

试试这样做: 在清理前,在失败分支中检查这些字段,然后停止轮询该任务。根据报告的原因决定需要修改的内容。求解失败会退款。

运行您的第一个任务。

使用 $5 工作区额度开始体验。

创建工作区
使用 cURL 生成 Kasada 请求头 · solvethree