Node.js और TypeScript में Cloudflare Turnstile कैसे हल करें

Cloudflare Turnstile दो रूपों में दिखाई देता है और उन्हें अलग-अलग कोड चाहिए। form के अंदर एक widget एक two-argument कॉल है। एक full-page interstitial challenge को पेज से स्क्रैप की गई दो अतिरिक्त वैल्यू चाहिए, और token तभी स्वीकार होगा जब आप वापस वही user agent भेजें जो solver ने इस्तेमाल किया था। वह आखिरी शर्त ही ऐसे tokens पैदा करती है जो बिल्कुल सही दिखते हैं और हर बार फेल हो जाते हैं।
इन्हें अलग पहचानना
| विजेट | Challenge page | |
|---|---|---|
| स्वरूप | एक उपयोग करने योग्य form के अंदर एक checkbox | फ़ुल-पेज interstitial, पेज ब्लॉक |
| cData और chlPageData चाहिए | नहीं | हां |
| लौटाए गए user agent की ज़रूरत है | नहीं | हां |
हमारा लाइव Turnstile डेमो widget वैरिएंट चलाता है, जो एक उपयोगी संदर्भ है जब आप यह पता लगा रहे हों कि आप किसे देख रहे हैं।
Setup
npm install capskip
const { CapSkip } = require('capskip');
const solver = new CapSkip({
host: '127.0.0.1',
port: 8080,
recaptchaTimeout: 300, // seconds, also covers Turnstile
});CapSkip लोकल रूप से हल करता है, इसलिए किसी भी call के सफल होने से पहले desktop app का चालू होना ज़रूरी है।
Widget mode
const result = await solver.turnstile( '0x4AAAAAAA...', // the data-sitekey attribute 'https://example.com/login', ); console.log(result.code); // cf-turnstile-response token
रखें result.code इसमें cf-turnstile-response फ़ील्ड और सबमिट। और कुछ की ज़रूरत नहीं है।
Challenge pages को दो और values चाहिए
एक इंटरस्टिशियल प्रति-रिक्वेस्ट स्टेट रखता है जिससे टोकन बँध जाता है। इसके दो हिस्सों को हल के साथ यात्रा करनी होती है:
- cData, के रूप में पास किया गया
data - chlPageData, के रूप में पास किया गया
pagedata
दोनों किसी form attribute के बजाय challenge page में ही रहते हैं, इसलिए हल करने से पहले page को fetch करना पड़ता है। किसी standard Cloudflare interstitial पर वे page’s के अपने challenge options object पर, sitekey के बगल में बैठते हैं। वे single use होते हैं और उसी page load से बंधे होते हैं, इसलिए cache करने के बजाय एक साथ fetch और हल करें।
const result = await solver.turnstile(sitekey, pageUrl, {
data: cData, // the cData value
pagedata: chlPageData, // the chlPageData value
action: 'managed', // optional, when the page declares one
});
console.log(result.code);
console.log(result.userAgent); // required for the next stepuser agent वैकल्पिक नहीं है
Turnstile token को उस browser fingerprint से बाँध देता है जिसने उसे बनाया, और user agent उस fingerprint का हिस्सा है। CapSkip वही लौटाता है जो उसने इस्तेमाल किया था result.userAgent। इसके बजाय token को Node’s के डिफ़ॉल्ट fetch user agent के साथ सबमिट करें और Cloudflare एक अन्यथा पूरी तरह वैध token को अस्वीकार कर देता है।
userAgent यह केवल Turnstile के लिए भरा जाता है। यह हर दूसरे कैप्चा प्रकार के लिए undefined होता है, यही वजह है कि यह उन लोगों को फँसाता है जो एक काम कर रहे reCAPTCHA helper को दोबारा इस्तेमाल करते हैं।
const response = await fetch(pageUrl, {
method: 'POST',
headers: {
// Send back the exact user agent the solve was performed with.
'User-Agent': result.userAgent,
'Content-Type': 'application/x-www-form-urlencoded',
},
body: new URLSearchParams({
'cf-turnstile-response': result.code,
}),
});अगर कोई token अस्वीकृत हो रहा है और cData ताज़ा है, तो लगभग हमेशा यही कारण होता है।
TypeScript
import { CapSkip, SolveResult } from 'capskip';
const solver = new CapSkip({ host: '127.0.0.1', port: 8080 });
const result: SolveResult = await solver.turnstile(sitekey, pageUrl);
// userAgent is optional on the type, because only Turnstile populates it.
if (result.userAgent) {
// safe to forward
}डेफिनिशन पैकेज के साथ आती हैं, इसलिए कोई नहीं है @types install। पर वैकल्पिक typing userAgent एक उपयोगी संकेत है: कंपाइलर आपको यह भूलने नहीं देगा कि अन्य कैप्चा टाइप्स इसे खाली छोड़ देते हैं।
प्रॉक्सी और concurrency
// Solve through the same egress you will submit from.
await solver.turnstile(sitekey, pageUrl, {
data: cData,
pagedata: chlPageData,
proxy: { type: 'HTTPS', uri: 'user:[email protected]:3128' },
});
// Several at once.
const results = await Promise.all(targets.map((t) =>
solver.turnstile(t.sitekey, t.url)));प्रॉक्सी Turnstile, reCAPTCHA और GeeTest के लिए काम करती हैं, लेकिन इमेज कैप्चा के लिए नहीं, जो कभी टारगेट साइट को छूते ही नहीं। चैलेंज पेजों के लिए, हर हल को अपना ताज़ा फेच किया गया cData चाहिए, इसलिए पहले से किसी बैच में करने के बजाय mapped फंक्शन के अंदर फेच करें।
अक्सर पूछे जाने वाले सवाल
क्या widgets को कभी cData की ज़रूरत होती है?
नहीं, और खाली values पास करने से हल मदद के बजाय विफल हो जाएगा। केवल full-page interstitial challenges इनका उपयोग करते हैं।
टोकन ठीक दिखता है लेकिन साइट इसे अस्वीकार कर देती है।
लगभग हमेशा user agent। इसका इस्तेमाल करके सबमिट करें result.userAgent बजाय इसके कि आपका HTTP client डिफ़ॉल्ट रूप से जो भी भेजता है। दूसरा सबसे संभावित कारण एक बासी cData है, जो एक single page load से बंधा होता है।
क्या मैं इसे Puppeteer के साथ उपयोग कर सकता हूँ?
हाँ, और यह अच्छी तरह जुड़ता है: लोड किए गए page से के साथ cData पढ़ें page.evaluate, इस SDK से हल करें, फिर आगे बढ़ने से पहले page पर वही user agent सेट करें। हमारा Node.js कैप्चा सॉल्वर पेज ऑटोमेशन पक्ष को कवर करता है।
सारांश
Widgets एक sitekey और एक URL लेते हैं। Challenge pages को चाहिए data और pagedata page से ताज़ा पढ़ा गया, और token को के साथ submit किया जाना चाहिए result.userAgent। बाकी सब कुछ सामान्य Promise हैंडलिंग है।
अन्य भाषाएँ इस पर हैं Cloudflare Turnstile सॉल्वर page, parameter विवरण यहाँ हैं API डॉक्युमेंटेशन, और व्यापक Node सतह इस पर Node.js कैप्चा सॉल्वर पेज। CapSkip एक है असीमित कैप्चा सॉल्वर जो आपके अपने hardware पर चलता है।
