Web sayfalarından veri elde etmek için önemli bir yetenek web kazımadır. Kullanıcı etkileşimi yoluyla dinamik olarak içerik yükleyen Pinterest ve Instagram bu tür web sitelerine örnektir. JavaScript tabanlı materyallerle çalışırken normal kazıma yöntemleri yetersiz kalmaktadır. Bu makalede, otomasyon aracı olarak Playwright üzerinde durulacak ve Javascript'in düzgün çalışmasını gerektiren bu tür dinamik sitelerden veri çekimi için lxml kullanılacaktır. Bu notta, bot olarak tespit edilmekten kaçınmak için Playwright'ta proxy'leri kullanmayı tartışabiliriz. Bu eğitimde, kaydırma ve gönderilerin yüklenmesini bekleme gibi kullanıcı davranışlarını simüle ederek tüm gönderi URL'lerini almak için Instagram profilini kazıyacağız.
Bu kılavuzda kullanacağımız araçlar:
Süreci, gönderi URL'lerini çıkarmak için bir Instagram profilini kazıma örneğini kullanarak, sayfada gezinme ve yeni verilerin yüklenmesini bekleme gibi kullanıcı eylemlerini simüle ederek göstereceğiz. Dinamik web siteleri içeriklerini AJAX istekleri aracılığıyla eşzamansız olarak yükler, bu da tüm sayfa içeriğine hemen erişilemeyeceği anlamına gelir.
Başlamadan önce gerekli paketleri yükleyin:
pip install playwright
pip install lxml
Ayrıca Playwright tarayıcılarını da yüklemeniz gerekir:
playwright install
Tarayıcıyı otomatikleştirmek, Instagram'ın dinamik içeriğini yüklemek ve daha fazla gönderi yüklemek için sayfada gezinmek için Playwright'ı kullanacağız. Temel bir otomasyon betiği oluşturalım:
Otomasyon betiği (Headless Browser):
import asyncio
from playwright.async_api import async_playwright
async def scrape_instagram():
async with async_playwright() as p:
browser = await p.chromium.launch(headless=True) # Başsız mod Görsel geri bildirim yok
page = await browser.new_page()
# Profil URL'sini ziyaret edin
await page.goto("https://www.instagram.com/profile name/", wait_until="networkidle")
# Daha fazla gönderi yüklemek için düğmeye tıklayın
await page.get_by_role("button", name="Show more posts from").click()
# Dinamik içerik yüklemek için sayfayı kaydırın
scroll_count = 5 # Bunu kaç kez kaydırmak istediğinize göre özelleştirin
for _ in range(scroll_count):
await page.evaluate('window.scrollBy(0, 700);')
await page.wait_for_timeout(3000) # Gönderilerin yüklenmesini bekleyin
await page.wait_for_load_state("networkidle")
# Sayfa içeriğini alın
content = await page.content()
await browser.close()
return content
# Eşzamansız işlevi çalıştırın
asyncio.run(scrape_instagram())
İçerik yüklendikten sonra, HTML'yi ayrıştırmak ve XPath kullanarak verileri ayıklamak için lxml kullanabiliriz. Bu durumda, profildeki tüm gönderilerin URL'lerini çıkarıyoruz.
Sayfa içeriğini ayrıştırma ve gönderi URL'lerini çıkarma:
from lxml import html
import json
def extract_post_urls(page_content):
# HTML içeriğini lxml kullanarak ayrıştırma
tree = html.fromstring(page_content)
# Gönderi URL'lerini ayıklamak için XPath
post_urls_xpath = '//a[contains(@href, "/p/")]/@href'
# URL'leri ayıklayın
post_urls = tree.xpath(post_urls_xpath)
# Göreli URL'leri mutlak hale dönüştürme
base_url = "https://www.instagram.com"
post_urls = [f"{base_url}{url}" for url in post_urls]
return post_urls
Çıkarılan verileri JSON biçiminde kaydetmek için örnek işlev:
def save_data(profile_url, post_urls):
data = {profile_url: post_urls}
with open('instagram_posts.json', 'w') as json_file:
json.dump(data, json_file, indent=4)
# URL'leri kazıyın ve ayıklayın
page_content = asyncio.run(scrape_instagram())
post_urls = extract_post_urls(page_content)
# Çıkarılan URL'leri bir JSON dosyasına kaydedin
save_data("https://www.instagram.com/profile name/", post_urls)
Dinamik web sitelerini kazımak için genellikle sonsuz kaydırmayı simüle etmeniz gerekir. Kodumuzda, JavaScript kullanarak sayfayı kaydırıyoruz:
(window.scrollBy(0, 700))
Ve bu komutu kullanarak yeni içeriğin yüklenmesini bekleyin:
wait_for_load_state("networkidle")
Instagram'ın katı hız sınırları ve anti-bot önlemleri vardır. Engellenmekten kaçınmak için, IP adreslerini döndürmek ve istekleri dağıtmak için proxy'leri kullanabilirsiniz. Playwright, proxy'leri kazıma otomasyonunuza entegre etmeyi kolaylaştırır.
Playwright'ta proxy'leri uygulama:
async def scrape_with_proxy():
async with async_playwright() as p:
browser = await p.chromium.launch(
headless=False,
proxy={"server": "http://your-proxy-server:port"}
)
page = await browser.new_page()
await page.goto("https://www.instagram.com/profile name/", wait_until="networkidle")
# Önceki gibi kazımaya devam edin...
Playwright ayrıca proxy'nin kullanıcı adı şifre olarak geçilmesini de destekler ve sunucu örneği aşağıda verilmiştir
async def scrape_with_proxy():
async with async_playwright() as p:
browser = await p.chromium.launch(
headless=False,
proxy={"server": "http://your-proxy-server:port", "username": "username", "password": "password"}
)
page = await browser.new_page()
await page.goto("https://www.instagram.com/profile name/", wait_until="networkidle")
# Önceki gibi kazımaya devam edin...
Proxy'ler IP yasaklarından, CAPTCHA zorluklarından kaçınmaya yardımcı olur ve Instagram gibi veri ağırlıklı veya kısıtlanmış web sitelerinin sorunsuz bir şekilde kazınmasını sağlar.
import asyncio
from playwright.async_api import async_playwright
from lxml import html
import json
# Tarayıcıyı otomatikleştirme ve proxy'lerle dinamik içeriği kazıma işlevi
async def scrape_instagram(profile_url, proxy=None):
async with async_playwright() as p:
# Sağlanmışsa tarayıcıyı proxy ile ayarlama
browser_options = {
'headless': True, # Eylemi görmek için başlı tarayıcıyı kullanın (başsız mod için True olarak ayarlanabilir)
}
if proxy:
browser_options['proxy'] = proxy
# Tarayıcıyı başlatın
browser = await p.chromium.launch(**browser_options)
page = await browser.new_page()
# Instagram profil sayfasını ziyaret edin
await page.goto(profile_url, wait_until="networkidle")
# "Daha fazla gönderi göster" düğmesine tıklamayı deneyin (isteğe bağlıdır, düğme bulunamazsa başarısız olabilir)
try:
await page.click('button:has-text("Show more posts from")')
except Exception as e:
print(f"No 'Show more posts' button found: {e}")
# Daha fazla gönderi yüklemek için sayfayı kaydırın
scroll_count = 5 # Gönderileri yüklemek için kaydırma sayısı
for _ in range(scroll_count):
await page.evaluate('window.scrollBy(0, 500);')
await page.wait_for_timeout(3000) # Yeni gönderilerin yüklenmesini bekleyin
await page.wait_for_load_state("networkidle")
# Kaydırdıktan sonra sayfa içeriğinin tamamını alın
content = await page.content()
await browser.close() # İşiniz bittiğinde tarayıcıyı kapatın
return content
# Kazınmış sayfa içeriğini ayrıştırma ve gönderi URL'lerini çıkarma işlevi
def extract_post_urls(page_content):
# HTML içeriğini lxml kullanarak ayrıştırma
tree = html.fromstring(page_content)
# Gönderi URL'lerini ayıklamak için XPath
post_urls_xpath = '//a[contains(@href, "/p/")]/@href'
# XPath kullanarak gönderi URL'lerini ayıklama
post_urls = tree.xpath(post_urls_xpath)
# Convert relative URLs to absolute URLs
base_url = "https://www.instagram.com"
post_urls = [f"{base_url}{url}" for url in post_urls]
return post_urls
# Çıkarılan gönderi URL'lerini bir JSON dosyasına kaydetme işlevi
def save_data(profile_url, post_urls):
# Verileri JSON biçiminde yapılandırın
data = {profile_url: post_urls}
# Verileri bir dosyaya kaydetme
with open('instagram_posts.json', 'w') as json_file:
json.dump(data, json_file, indent=4)
print(f"Data saved to instagram_posts.json")
# Kazıyıcıyı çalıştırmak ve verileri kaydetmek için ana işlev
async def main():
# Instagram profil URL'sini tanımlayın
profile_url = "https://www.instagram.com/profile name/"
# İsteğe bağlı olarak, bir proxy ayarlayın
proxy = {"server": "server", "username": "username", "password": "password"} # Proxy gerekmiyorsa Yok seçeneğini kullanın
# Instagram sayfasını proxy'lerle kazıyın
page_content = await scrape_instagram(profile_url, proxy=proxy)
# Kazınan sayfa içeriğinden gönderi URL'lerini ayıklayın
post_urls = extract_post_urls(page_content)
# Çıkarılan gönderi URL'lerini bir JSON dosyasına kaydedin
save_data(profile_url, post_urls)
if __name__ == '__main__':
asyncio.run(main())
Playwright dinamik web sitelerini kazımak için mükemmel bir seçim olsa da, diğer araçlar farklı senaryolar için uygun olabilir:
Her araç benzersiz güçlü yönler sunar ve projenin özel ihtiyaçlarına ve koşullarına göre seçilebilir.
JavaScript ve AJAX isteklerini aktif olarak kullanan dinamik web sitelerinin başarılı bir şekilde kazınması için, sonsuz kaydırma ve karmaşık etkileşimli öğeleri verimli bir şekilde işleyebilen güçlü araçlar gereklidir. Microsoft'un tam tarayıcı otomasyonu sağlayan bir aracı olan Playwright, Instagram gibi platformlar için ideal bir seçimdir. HTML ayrıştırma için lxml kütüphanesi ile birlikte Playwright, veri çıkarmayı büyük ölçüde basitleştirerek sayfa öğeleriyle etkileşimlerin otomasyonuna ve manuel müdahale olmadan ayrıştırma işlemine olanak tanır. Ayrıca, proxy sunucularının kullanımı anti-bot korumasını atlatmaya yardımcı olur ve IP engellemesini önleyerek istikrarlı ve kesintisiz kazıma işlemleri sağlar.
Yorumlar: 0