Every reCAPTCHA solve through CaptchaAI requires the correct sitekey and page URL. Some CAPTCHA types also need additional parameters — action (v3), data-s (Google sites), or enterprise flag. This guide covers every extraction method.
Parameters by reCAPTCHA version
| Parameter | v2 Standard | v2 Invisible | v3 | Enterprise |
|---|---|---|---|---|
googlekey (sitekey) |
Required | Required | Required | Required |
pageurl |
Required | Required | Required | Required |
invisible |
— | 1 |
— | — |
action |
— | — | Required | Sometimes |
data-s |
Sometimes | Sometimes | — | — |
enterprise |
— | — | — | 1 |
Method 1: HTML attribute extraction
From data-sitekey attribute
import re
import requests
url = "https://example.com/login"
html = requests.get(url).text
# Find data-sitekey
match = re.search(r'data-sitekey=["\']([A-Za-z0-9_-]+)["\']', html)
if match:
sitekey = match.group(1)
print(f"Sitekey: {sitekey}")
# Check if invisible
invisible_match = re.search(r'data-size=["\']invisible["\']', html)
is_invisible = bool(invisible_match)
print(f"Invisible: {is_invisible}")
# Find callback
callback_match = re.search(r'data-callback=["\'](\w+)["\']', html)
callback = callback_match.group(1) if callback_match else None
print(f"Callback: {callback}")
# Check for data-s (Google-owned sites)
data_s_match = re.search(r'data-s=["\']([^"\']+)["\']', html)
data_s = data_s_match.group(1) if data_s_match else None
print(f"data-s: {data_s}")
JavaScript (Puppeteer)
const puppeteer = require('puppeteer');
const browser = await puppeteer.launch();
const page = await browser.newPage();
await page.goto('https://example.com/login', { waitUntil: 'networkidle2' });
const params = await page.evaluate(() => {
const widget = document.querySelector('.g-recaptcha');
if (!widget) return null;
return {
sitekey: widget.getAttribute('data-sitekey'),
size: widget.getAttribute('data-size'),
callback: widget.getAttribute('data-callback'),
dataS: widget.getAttribute('data-s'),
invisible: widget.getAttribute('data-size') === 'invisible',
};
});
console.log(params);
Method 2: Script tag extraction
reCAPTCHA v3 and Enterprise sitekeys
v3 sitekeys are embedded in the script URL:
# Find sitekey from script src
v3_match = re.search(
r'recaptcha/(?:api|enterprise)\.js\?.*?render=([A-Za-z0-9_-]+)',
html
)
if v3_match:
sitekey = v3_match.group(1)
print(f"v3 Sitekey: {sitekey}")
# Check enterprise
is_enterprise = 'enterprise.js' in html
print(f"Enterprise: {is_enterprise}")
Finding the action parameter
The action is passed in JavaScript code, not in HTML attributes:
# Search for grecaptcha.execute calls
action_match = re.search(
r'grecaptcha\.execute\s*\([^,]+,\s*\{[^}]*action\s*:\s*["\']([^"\']+)',
html
)
if action_match:
action = action_match.group(1)
print(f"Action: {action}")
Method 3: Iframe src extraction
When reCAPTCHA is rendered inside an iframe:
# Find reCAPTCHA iframe
iframe_match = re.search(
r'<iframe[^>]+src=["\']([^"\']*recaptcha/api2/anchor[^"\']*)["\']',
html
)
if iframe_match:
iframe_src = iframe_match.group(1)
sitekey_match = re.search(r'k=([A-Za-z0-9_-]+)', iframe_src)
if sitekey_match:
sitekey = sitekey_match.group(1)
print(f"Iframe sitekey: {sitekey}")
Method 4: JavaScript rendering extraction
For pages that render reCAPTCHA dynamically with grecaptcha.render():
# Find grecaptcha.render calls
render_match = re.search(
r'grecaptcha\.render\s*\([^,]*,\s*\{([^}]+)\}',
html
)
if render_match:
config = render_match.group(1)
sk = re.search(r'sitekey\s*:\s*["\']([A-Za-z0-9_-]+)', config)
cb = re.search(r'callback\s*:\s*["\']?(\w+)', config)
sz = re.search(r'size\s*:\s*["\'](\w+)', config)
print(f"Sitekey: {sk.group(1) if sk else 'not found'}")
print(f"Callback: {cb.group(1) if cb else 'not found'}")
print(f"Size: {sz.group(1) if sz else 'not found'}")
Complete extraction function
import re
import requests
def extract_recaptcha_params(url):
html = requests.get(url, timeout=15).text
params = {"pageurl": url}
# Sitekey from data-sitekey
sk = re.search(r'data-sitekey=["\']([A-Za-z0-9_-]+)', html)
if sk:
params["sitekey"] = sk.group(1)
# Sitekey from script render parameter (v3)
if "sitekey" not in params:
v3 = re.search(r'render=([A-Za-z0-9_-]{20,})', html)
if v3:
params["sitekey"] = v3.group(1)
# Sitekey from iframe
if "sitekey" not in params:
iframe = re.search(r'recaptcha.*?k=([A-Za-z0-9_-]+)', html)
if iframe:
params["sitekey"] = iframe.group(1)
# Sitekey from grecaptcha.render
if "sitekey" not in params:
render = re.search(r'sitekey\s*:\s*["\']([A-Za-z0-9_-]+)', html)
if render:
params["sitekey"] = render.group(1)
# Version detection
if re.search(r'data-size=["\']invisible', html):
params["invisible"] = True
if 'enterprise.js' in html:
params["enterprise"] = True
# Action (v3)
action = re.search(
r'action\s*:\s*["\']([^"\']+)',
html[html.find('grecaptcha.execute'):] if 'grecaptcha.execute' in html else ''
)
if action:
params["action"] = action.group(1)
# data-s
ds = re.search(r'data-s=["\']([^"\']+)', html)
if ds:
params["data_s"] = ds.group(1)
# Callback
cb = re.search(r'data-callback=["\'](\w+)', html)
if cb:
params["callback"] = cb.group(1)
return params
# Usage
params = extract_recaptcha_params("https://example.com/login")
for k, v in params.items():
print(f" {k}: {v}")
Expected output:
pageurl: https://example.com/login
sitekey: 6Le-SITEKEY-abc123
invisible: True
callback: onCaptchaComplete
Submitting extracted parameters to CaptchaAI
data = {
"key": API_KEY,
"method": "userrecaptcha",
"googlekey": params["sitekey"],
"pageurl": params["pageurl"],
"json": "1",
}
if params.get("invisible"):
data["invisible"] = "1"
if params.get("enterprise"):
data["enterprise"] = "1"
if params.get("action"):
data["action"] = params["action"]
if params.get("data_s"):
data["data-s"] = params["data_s"]
resp = requests.post("https://ocr.captchaai.com/in.php", data=data).json()
Troubleshooting
| Problem | Cause | Fix |
|---|---|---|
| No sitekey found | Page uses dynamic rendering | Use Puppeteer/Selenium instead of static HTML |
| Wrong sitekey | Multiple reCAPTCHA instances | Check which widget maps to the form you're submitting |
| Action not found | Defined in external JS file | Fetch and search linked JavaScript files |
data-s changes per request |
Google regenerates it | Extract fresh data-s for each solve |
FAQ
Can I extract parameters without loading the page in a browser?
Yes, for most sites — the sitekey is in the HTML source. But JavaScript-rendered CAPTCHAs require a browser or headless browser.
Is the sitekey the same as the API key?
No. The sitekey is a public key assigned to the website. It's safe to share and is visible in the page source.
Use extracted parameters with CaptchaAI for reliable solving
Get your API key at captchaai.com.
Discussions (0)
Join the conversation
Sign in to share your opinion.
Sign InNo comments yet.