🎯 कस्टमाइज़ करने योग्य, डिटेक्शन-प्रतिरोधी क्लाउड ब्राउज़र जो स्व-विकसित Chromium द्वारा संचालित है, वेब क्रॉलर और एआई एजेंट्स के लिए डिज़ाइन किया गया। 👉अभी आज़माएं
वापस ब्लॉग पर

शैडो डोम को प्लेव्राइट और स्क्रेपलेस के साथ कैसे स्क्रैप करें

Daniel Kim
Daniel Kim

Lead Scraping Automation Engineer

30-Jul-2026

TL;DR:

  • शैडो DOM ऐसा टेक्स्ट दिखा सकता है जो मेज़बान तत्व के सामान्य लाइट DOM में मौजूद नहीं है। JavaScript कस्टम तत्व लोड होने के बाद एक शैडो रूट के अंदर दृश्य सामग्री बना सकता है।
  • प्लेवरीट CSS और टेक्स्ट लोकेटर्स ओपन शैडो रूट्स को पार कर सकते हैं। वही सेलेक्टर document.querySelector के साथ विफल हो जाता है क्योंकि दस्तावेज़-स्तरीय DOM क्वेरी शैडो सीमा पर रुक जाती हैं।
  • बंद शैडो रूट्स और XPath को अलग अपेक्षाएँ चाहिए। प्लेवरीट लोकेटर्स बंद रूट्स को नहीं पार करते हैं, और XPath सेलेक्टर्स स्वत: शैडो DOM ट्रैवर्सल का समर्थन नहीं करते हैं।
  • शैडो DOM निकालने की लॉजिक ब्राउज़र ट्रांसपोर्ट से स्वतंत्र होती है। कार्यप्रणाली की स्थानीय मान्यता करें, फिर एक होस्टेड ब्राउज़र या प्रबंधित ईग्रस की आवश्यकता होने पर एक ही लोकेटर्स को Scrapeless CDP कनेक्शन के जरिए पुन: उपयोग करें।
  • शुरू करने के लिए स्वतंत्र। नए Scrapeless खातों में मुफ्त स्क्रैपिंग ब्राउज़र रनटाइम शामिल है—app.scrapeless.com पर साइन अप करें।

एक शैडो DOM घटक ऐसा टेक्स्ट प्रदर्शित कर सकता है जो मेज़बान तत्व के सामान्य लाइट-DOM बच्चों में अनुपस्थित है। यह गाइड प्लेवरीट का उपयोग करते हुए एक वास्तविक ओपन शैडो रूट को पार करना दिखाती है, बताती है कि दस्तावेज़-स्तरीय सेलेक्टर कुछ क्यों लौटाता है, और उस निकालने की लॉजिक को Scrapeless स्क्रैपिंग ब्राउज़र कनेक्शन से अलग करती है जो उसी कोड को क्लाउड ब्राउज़र में चलाती है।

स्क्रैपर के लिए शैडो DOM क्या बदलता है

शैडो DOM एक कस्टम तत्व को एक इंकैप्सुलेटेड सबट्री देता है। पृष्ठ का मुख्य दस्तावेज़ मेज़बान टैग को देख सकता है, लेकिन सामान्य DOM API स्वचालित रूप से उस मेज़बान से शैडो रूट में नहीं जाती।

नीचे उपयोग किए गए सार्वजनिक MDN डेमो में, स्रोत में <popup-info> मेज़बान होता है जिसमें data-text विशेषता होती है। एक डिफर्ड स्क्रिप्ट उस टैग को अपग्रेड करती है, attachShadow({ mode: "open" }) को कॉल करती है, और एक आंतरिक .info स्पैन बनाती है। ब्राउज़र उस स्पैन से सहायक टेक्स्ट प्रदर्शित करता है। प्रारंभिक HTML में स्पैन मौजूद नहीं होता।

MDN का शैडो DOM गाइड सीमा और ओपन और क्लोज्ड रूट्स के बीच अंतर को परिभाषित करता है। यह भेद महत्वपूर्ण है: एक ओपन रूट element.shadowRoot को उजागर करता है; एक क्लोज्ड रूट उस API के माध्यम से null लौटाता है।

Scrapeless के साथ Playwright का उपयोग क्यों करें

प्लेवरीट लोकेटर्स सामान्य CSS और टेक्स्ट लुकअप के लिए ओपन शैडो रूट्स में प्रवेश करते हैं। प्लेवरीट लोकेटर डॉक्यूमेंटेशन दो अपवाद बताता है: XPath शैडो रूट्स को नहीं पार करता, और क्लोज्ड-मोड रूट्स का समर्थन नहीं किया जाता है।

Traversal कोड इस पर निर्भर नहीं करता कि Chromium कहां चल रहा है। एक स्थानीय ब्राउज़र सार्वजनिक डेमो के लिए पर्याप्त है; Scrapeless Scraping Browser तब उपयोगी होता है जब लक्ष्य को एक होस्टेड ब्राउज़र, प्रबंधित फिंगरप्रिंट, निवासीय ईग्रस, या एक स्थायी क्लाउड सत्र की आवश्यकता होती है। प्लेवरीट उस ब्राउज़र तक पहुँचता है connect_over_cdp API के माध्यम से।

आवश्यकताएँ

  • Python 3.10 या उससे अधिक।
  • playwright 1.59.0 या कोई वर्तमान संगत संस्करण।
  • नीचे पूरी तरह से निष्पादन योग्य फॉलबैक के लिए एक स्थानीय क्रोम/क्रोमियम रनटाइम।
  • एक वित्त पोषित Scrapeless खाता और क्लाउड कनेक्शन के लिए SCRAPELESS_API_KEY। सत्यापन खाते ने नए ब्राउज़र सत्रों के लिए कोड 14500 वापस किया, इसलिए क्लाउड कनेक्शन ब्लॉक को एक आवश्यकतानुपात अंतर के रूप में चिह्नित किया गया है न कि सफल के रूप में दिखाया गया है।

स्थापित करें

bash Copy
python -m pip install "playwright==1.59.0"

सत्यापन होस्ट में पहले से ही Google Chrome /usr/bin/google-chrome पर है। यदि आपकी मशीन में नहीं है, तो परियोजना की सामान्य ब्राउज़र सेटअप कमांड का उपयोग करके एक प्लेवरीट-प्रबंधित क्रोमियम स्थापित करें।

Scrapeless स्क्रैपिंग ब्राउज़र से कनेक्ट करें

नोट: इस कनेक्शन के लिए वित्त पोषित Scrapeless ब्राउज़र बैलेंस की आवश्यकता होती है। अंतिम सत्यापन के लिए उपयोग की गई खाता insufficient balance, please recharge first लौटाता है; इसे अपने वित्त पोषित कुंजी के साथ चलाएं। इस अनुभाग के बाद ट्रैवर्सल ब्लॉक्स पूरी तरह से उसी सार्वजनिक पृष्ठ के खिलाफ स्थानीय क्रोम में चले।

python Copy
import os
from urllib.parse import urlencode
from playwright.sync_api import sync_playwright

params = urlencode({
    "token": os.environ["SCRAPELESS_API_KEY"],
    "sessionTTL": 120,
    "proxyCountry": "US",
})
cdp_url = f"wss://browser.scrapeless.com/api/v2/browser?{params}"

with sync_playwright() as p:
    browser = p.chromium.connect_over_cdp(cdp_url)
    page = browser.contexts[0].pages[0]
    # इस पृष्ठ के साथ नीचे निकालने के चरण चलाएँ।
    browser.close()

Scrapeless डेवलपर दस्तावेज़ कनेक्शन पैरामीटर के लिए वर्तमान स्रोत हैं। एक बार जब page मौजूद होता है, तो शैडो DOM लुकअप सामान्य प्लेवरीट होता है।

मेज़बान और इसके ओपन रूट का निरीक्षण करें

MDN घटक डेमो छोटा और सार्वजनिक है:

python Copy
TARGET_URL = (
    "https://mdn.github.io/web-components-examples/"
    "popup-info-box-web-component/"
)

page.goto(TARGET_URL, wait_until="domcontentloaded")
page.wait_for_selector("popup-info .info")

host = page.locator("popup-info")
print("host light-DOM text:", repr(host.inner_text()))
print("shadow mode:", host.evaluate("element => element.shadowRoot.mode"))
text Copy
host light-DOM text: ''
shadow mode: open

खाली होस्ट टेक्स्ट इस बात का साक्ष्य नहीं है कि घटक में कोई डेटा नहीं है। इसका अर्थ है कि होस्ट में कोई सामान्य बाल टेक्स्ट नहीं है। वास्तविक .info नोड खुली छाया जड़ के नीचे स्थित है जो कस्टम तत्व अपग्रेड के बाद बनाई जाती है।

दस्तावेज़ चयनकर्ता की सीमा पर रुकने का प्रमाणीकरण करें

दस्तावेज़ से एक साधारण ब्राउज़र डॉम क्वेरी चलाएँ:

python Copy
plain_match = page.evaluate(
    "document.querySelector('popup-info .info') !== null"
)
print("document query found inner node:", plain_match)
text Copy
document query found inner node: False

चयनकर्ता मान्य CSS है। असफलता दायरे से आती है: document.querySelector दस्तावेज़ पेड़ की खोज करता है और होस्ट के छाया पेड़ में नहीं उतरता।

एक Playwright लोकेटर को खुले रूट में प्रवेश करने दें

Playwright की सामान्य लोकेटर श्रृंखला खुले रूट को पार करती है:

python Copy
info = page.locator("popup-info .info")
record = {
    "host": "popup-info",
    "shadow_mode": host.evaluate("element => element.shadowRoot.mode"),
    "text": info.inner_text(),
    "source_url": page.url,
}

print("inner matches:", info.count())
print("help text:", record["text"])
print("text chars:", len(record["text"]))
text Copy
inner matches: 1
help text: Your card validation code (CVC) is an extra security feature — it is the last 3 or 4 numbers on the back of your card.
text chars: 118

वह टेक्स्ट घटक का वास्तविक data-text मान है जो छाया-रूट स्पैन में कॉपी किया गया है। वर्णों की गणना में विराम चिह्न और स्थान शामिल हैं, इसलिए यह एक खाली तत्व या आइकन के वैकल्पिक टेक्स्ट को अनजाने में निकालने के खिलाफ एक उपयोगी सुरक्षा है।

क्या आप उसी लोकेटर को एक होस्टेड ब्राउज़र में ले जाने के लिए तैयार हैं? एक मुफ्त Scrapeless खाता बनाएं और ब्राउज़र निर्माण के बाद हर पंक्ति को अपरिवर्तित रखें।

पूर्ण स्थानीय सत्यापन स्क्रिप्ट

यह स्क्रिप्ट स्थानीय Chrome में पूरे निदान को चलाती है। launch(...) को उपरोक्त CDP कनेक्शन से प्रतिस्थापित करना इसे Scrapeless में बिना निकासी तर्क को बदले स्थानांतरित करता है:

python Copy
from playwright.sync_api import sync_playwright

TARGET_URL = (
    "https://mdn.github.io/web-components-examples/"
    "popup-info-box-web-component/"
)

with sync_playwright() as p:
    browser = p.chromium.launch(
        executable_path="/usr/bin/google-chrome",
        headless=True,
    )
    page = browser.new_page()
    page.goto(TARGET_URL, wait_until="domcontentloaded")
    page.wait_for_selector("popup-info .info")

    host = page.locator("popup-info")
    info = page.locator("popup-info .info")
    host_text = host.inner_text()
    shadow_mode = host.evaluate("element => element.shadowRoot.mode")
    plain_match = page.evaluate(
        "document.querySelector('popup-info .info') !== null"
    )
    help_text = info.inner_text()

    assert shadow_mode == "open"
    assert not plain_match
    assert "card validation code" in help_text

    print("page title:", page.title())
    print("host light-DOM text:", repr(host_text))
    print("shadow mode:", shadow_mode)
    print("document query found inner node:", plain_match)
    print("inner matches:", info.count())
    print("help text:", help_text)
    print("text chars:", len(help_text))
    browser.close()

यह रन सीमा को साबित करता है न कि केवल एक सफल लोकेटर दिखाता है: हल्का-डीओएम टेक्स्ट खाली है, दस्तावेज़ चयनकर्ता गलत है, रूट open की रिपोर्ट करता है, और Playwright एक 118-चर मदद स्ट्रिंग लौटाता है।

खुले और बंद रूट का क्या अर्थ है

ओपन रूट

attachShadow({mode: "open"}) host.shadowRoot को उपलब्ध छोड़ता है। Playwright लोकेटर इसे CSS/पाठ चयनकर्ताओं के साथ पार कर सकते हैं। नेस्टेड ओपन रूट्स को समान तरीके से संभाला जाता है, हालांकि प्रत्येक घटक अलग अलग समय पर लोड हो सकता है।

बंद रूट

attachShadow({mode: "closed"}) host.shadowRoot को null लौटाने के लिए बनाता है। Playwright के सामान्य लोकेटर इसे नहीं पार करते। स्क्रिप्ट इंजेक्शन या ब्राउज़र इंस्ट्रुमेंटेशन को एक सार्वभौमिक समाधान के रूप में प्रस्तुत न करें: एक बंद रूट एक स्पष्ट संपीड़न सीमा है, और पृष्ठ कोड को बदलने से उस व्यवहार में परिवर्तन हो सकता है जिसे आप मापना चाहते थे।

स्लॉटेड सामग्री

एक <slot> छाया-树 लेआउट के भीतर हल्के-डीओएम बच्चों को प्रदर्शित करती है। असाइन किए गए नोड्स अभी भी होस्ट के हल्के डॉम के अंतर्गत आते हैं, इसलिए उनका स्वामित्व और चयनकर्ता व्यवहार उन तत्वों से भिन्न होता है जो छाया रूट के भीतर बनाए गए हैं। यह तय करने से पहले कि डेटा किस पक्ष के पास है, लाइव डॉम की जांच करें।

सामान्य छाया डॉम विफलता मोड

होस्ट मौजूद है लेकिन आंतरिक लोकेटर समय समाप्त हो जाता है

कस्टम तत्व अभी तक अपडेट नहीं हुआ हो सकता है, इसका जावास्क्रिप्ट विफल हो सकता है, या चयनकर्ता एक बंद रूट को लक्षित कर सकता है। असली तत्परता मार्कर के रूप में आंतरिक तत्व पर इंतजार करें और चयनकर्ताओं को बदलने से पहले कंसोल त्रुटियों की जांच करें।

एक्सपाथ कुछ नहीं पाता

CSS या पाठ स्थानक का उपयोग करें। प्लेयराइट के प्रलेखित शैडोTraversal एक्सपाथ चयनकर्ताओं पर लागू नहीं होते हैं।

एक घुसे हुए घटक आंशिक पाठ लौटाता है

एक बड़े होस्ट पर inner_text() कॉल करने के बजाय गहरे स्थिर तत्व का पता लगाएं। यह स्लॉट पाठ, दृश्य रूप से छिपे हुए लेबल और घुसे हुए घटक के आउटपुट को मिलाने से रोकता है।

स्रोत एचटीएमएल में कोई आंतरिक नोड नहीं है

यह सामान्य है जब जावास्क्रिप्ट छायादार पेड़ बनाती है। एक ब्राउज़र का उपयोग करें। एक HTTP पार्सर केवल स्रोत प्रतिक्रिया को देखता है और लोड के बाद बनाए गए उप-पत्रक को नहीं देख सकता है।

निष्कर्ष

शैडो डोम स्क्रैपिंग एक स्कोप समस्या है इससे पहले कि यह एक चयनकर्ता समस्या हो। साबित करें कि कौन सा पेड़ नोड का मालिक है, कस्टम तत्व के अपग्रेड होने का इंतजार करें, और ओपन रूट्स के लिए प्लेयराइट के CSS/पाठ स्थानकों का उपयोग करें। बंद-रूट सीमा को ईमानदार रखें। ब्राउज़र परिवहन अलग है: सार्वजनिक परीक्षण सतह के लिए स्थानीय रूप से चलाएं, फिर जब लक्ष्य को एक होस्टेड एंटी-डिटेक्शन ब्राउज़र या प्रबंधित निकासी की आवश्यकता हो तो ब्राउज़र निर्माण को स्क्रैपलेस सीडीपी एंडपॉइंट पर स्विच करें।

स्क्रैपलेस के साथ शुरू करें, स्क्रैपलेस मूल्य निर्धारण की समीक्षा करें, और जानें कि क्रोम देव टूल प्रोटोकॉल क्या नियंत्रित करता है आसपास के सीडीपी आर्किटेक्चर के लिए।

सामान्य प्रश्न

प्रश्न: क्या प्लेयराइट एक ओपन शैडो डोम रूट को स्क्रैप कर सकता है?

हाँ। प्लेयराइट के CSS और पाठ स्थानक खुले शैडो रूट को छेदते हैं, इसलिए एक स्थानक जैसे page.locator("popup-info .info") आंतरिक नोड तक पहुँच सकता है।

प्रश्न: समान चयनकर्ता पर document.querySelector क्यों विफल होता है?

document.querySelector दस्तावेज़ वृक्ष की खोज करता है और छाया मेज़बान पर रुक जाता है। आपको खुद खुले रूट के माध्यम से पूछताछ करनी चाहिए या ऐसा स्थानक उपयोग करना चाहिए जो उस traversal को करता है।

प्रश्न: क्या प्लेयराइट एक बंद शैडो रूट को छेद सकता है?

नहीं, अपने सामान्य स्थानक व्यवहार के माध्यम से नहीं। एक बंद रूट host.shadowRoot से null लौटाता है और यह एक प्रलेखित असमर्थित सीमा है।

प्रश्न: क्या एक्सपाथ शैडो डोम के अंदर काम करता है?

नहीं। प्लेयराइट की आधिकारिक स्थानक मार्गदर्शन कहती है कि एक्सपाथ चयनकर्ता शैडो रूट को नहीं छेदते; CSS या पाठ स्थानक का उपयोग करें।

प्रश्न: मैं घुसे हुए खुले शैडो रूट को कैसे संभालूं?

स्थिर आंतरिक तत्व की ओर स्थानकों को जोड़ें और उस तत्व के लिए इंतजार करें। प्लेयराइट कई खुले रूट्स को पार कर सकता है, लेकिन प्रत्येक कस्टम तत्व असिंक्रोनसली अपग्रेड हो सकता है।

प्रश्न: क्या मुझे शैडो डोम स्क्रैपिंग के लिए एक ब्राउज़र की आवश्यकता है?

हाँ जब जावास्क्रिप्ट छायादार पेड़ बनाता है। एक साधारण HTTP प्रतिक्रिया होस्ट मार्कअप और स्क्रिप्ट्स को शामिल करती है, न कि निष्पादन के बाद उत्पन्न जीवित उप-पत्रक।

प्रश्न: क्या शैडो डोम स्क्रैपिंग कानूनी है?

DOM तंत्र अनुमति का निर्णय नहीं करता है। लक्षित की शर्तों और रोबोट्स निर्देशों की समीक्षा करें, सार्वजनिक डेटा का उपयोग करें, अनुरोध की मात्रा को सीमित करें, और संवेदनशील या वाणिज्यिक संग्रह के लिए कानूनी सलाह लें।

स्क्रैपलेस में, हम केवल सार्वजनिक रूप से उपलब्ध डेटा का उपयोग करते हैं, जबकि लागू कानूनों, विनियमों और वेबसाइट गोपनीयता नीतियों का सख्ती से अनुपालन करते हैं। इस ब्लॉग में सामग्री केवल प्रदर्शन उद्देश्यों के लिए है और इसमें कोई अवैध या उल्लंघन करने वाली गतिविधियों को शामिल नहीं किया गया है। हम इस ब्लॉग या तृतीय-पक्ष लिंक से जानकारी के उपयोग के लिए सभी देयता को कोई गारंटी नहीं देते हैं और सभी देयता का खुलासा करते हैं। किसी भी स्क्रैपिंग गतिविधियों में संलग्न होने से पहले, अपने कानूनी सलाहकार से परामर्श करें और लक्ष्य वेबसाइट की सेवा की शर्तों की समीक्षा करें या आवश्यक अनुमतियाँ प्राप्त करें।

सबसे लोकप्रिय लेख

सूची