PHP로 reCAPTCHA Enterprise 해결하기
PHP에서 solvethree를 직접 호출할 수 있습니다. 아래 예제는 reCAPTCHA v3 Enterprise 토큰을 요청하고, 작업이 끝날 때까지 상태를 확인하며, 해결에 실패하면 중단합니다.
이 페이지의 내용
실행 전 준비
cURL 확장이 포함된 PHP 8+를 사용하세요. cURL 확장을 활성화한 서버에서 실행하세요.
- 콘솔에서 대상 호스트 이름에 대한 활성 사이트 프로필을 생성하세요. 사이트 프로필 설정을 참고하세요.
SOLVETHREE_API_KEY를 워크스페이스 API 키로,SOLVETHREE_PROXY를 HTTP(S) 프록시 URL로 설정하세요.accounts.example.com과login을 호스트 이름과 페이지에서 사용하는 액션으로 바꾸세요.site에는 스킴이나 경로 없이 호스트 이름을 사용하세요.
작업 생성 및 결과 대기
코드를 solve.php로 저장하고 php solve.php를 실행하세요.
<?php
// Requires PHP 8+ with the cURL extension.
$apiKey = getenv('SOLVETHREE_API_KEY');
$proxy = getenv('SOLVETHREE_PROXY');
if (!$apiKey || !$proxy) throw new RuntimeException('Set the API key and proxy');
function api(string $path, ?array $body = null): array {
global $apiKey, $deadline;
$remaining = $deadline - microtime(true);
if ($remaining <= 0) throw new RuntimeException("Keep the task ID and resume polling");
$curl = curl_init('https://api.solvethree.com/v1' . $path);
curl_setopt_array($curl, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_TIMEOUT_MS => min(30000, max(1, (int) ceil($remaining * 1000))),
CURLOPT_HTTPHEADER => ['Authorization: Bearer ' . $apiKey, 'Content-Type: application/json'],
]);
if ($body !== null) {
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, json_encode($body, JSON_THROW_ON_ERROR));
}
$raw = curl_exec($curl);
$error = curl_error($curl);
$status = curl_getinfo($curl, CURLINFO_RESPONSE_CODE);
curl_close($curl);
if ($raw === false) throw new RuntimeException('Connection failed: ' . $error);
if ($status < 200 || $status >= 300) throw new RuntimeException('API HTTP ' . $status);
return json_decode($raw, true, 512, JSON_THROW_ON_ERROR);
}
$requestId = bin2hex(random_bytes(16)); // Save this with the task inputs for recovery.
$deadline = microtime(true) + 180;
$task = api('/tasks?waitMs=0', [
'site' => 'accounts.example.com', 'action' => 'login',
'proxy' => $proxy, 'requestId' => $requestId,
]);
while (in_array($task['status'], ['pending', 'solving'], true)) {
if (microtime(true) >= $deadline) throw new RuntimeException('Keep the task ID and resume polling');
$task = api('/tasks/' . rawurlencode($task['id']) . '?waitMs=15000');
if (in_array($task['status'], ['pending', 'solving'], true)) usleep(1000000);
}
if ($task['status'] !== 'ready') throw new RuntimeException(
($task['errorCode'] ?? 'Unexpected task state') . ': ' . ($task['error'] ?? '')
);
$solution = $task['solution'];
// Use $solution['token'], ['userAgent'] and ['secChUa'] with the same proxy.
echo 'Ready task: ' . $task['id'] . PHP_EOL;POST는 waitMs=0을 사용해 작업을 즉시 반환합니다. 이후 각 GET은 업데이트를 최대 15초 동안 기다립니다. 루프는 pending 또는 solving 상태에서 계속되며, ready 또는 failed 상태에서 중단됩니다.
요청의 기본값은 Enterprise v3입니다. 일반 v3를 사용하려면 recaptchaType: v3를 추가하세요. reCAPTCHA 작업 본문에 type과 url을 넣지 마세요.
애플리케이션에서 토큰 사용하기
토큰은 $solution['token']입니다. 프로그램이 출력하는 작업 ID는 작업 조회용입니다. 애플리케이션의 CAPTCHA 필드에는 토큰 값을 사용하세요.
대상 요청에서 $solution['userAgent']를 User-Agent로, $solution['secChUa']를 sec-ch-ua로 사용하세요.
해결에 사용한 것과 동일한 프록시를 통해 해당 요청을 보내세요. 그런 다음 애플리케이션의 응답을 확인하세요. 토큰이 생성되었다고 해서 대상이 요청을 수락했다는 뜻은 아닙니다.
요청 실패 시
실패한 작업에는 errorCode와 error가 포함되며, 예제는 실행을 중단하고 이를 보고합니다. 실패한 해결 건은 환불됩니다. 401이나 402 같은 HTTP 오류는 별도의 요청 문제이므로, 재시도하기 전에 API 오류 레퍼런스를 확인하세요.
시간 초과나 프로세스 재시작 후 복구해야 한다면 requestId와 정확한 작업 입력값을 보관하세요. 작업 ID가 있으면 해당 작업을 폴링하세요. 없다면 동일한 requestId로 원래 입력값을 다시 보내세요. 단순히 프로그램을 재시작하면 다른 ID가 생성되어 추가로 과금되는 해결 작업이 만들어질 수 있습니다.
호출 측은 기한이 지나면 대기를 중단하지만, 이미 생성된 작업이 취소되는 것은 아닙니다. 전체 절차는 폴링 및 시간 초과 복구를 참고하세요.
첫 작업을 실행하세요.
워크스페이스 크레딧 $5로 시작하세요.