Не работает пагинация при парсинге python

Пирасинге торговой площадки steam с толкнулся с проблемой. Все страницы написанный под тегом span. Я решил перебором подставлять номера страницы в сслыку, получается https://steamcommunity.com/market/searchq=&category_570_Hero%5B%5D=any&category_570_Slot%5B%5D=any&category_570_Type%5B%5D=any&appid=570#p(1, 2, 3 и т.д)_popular_desc . Но если я вставляю ссылку 3 страницы с номером страницы, у меня всегда парсится первая страница. Код предоставляю отрезок кода и результаты работы программы. В csv всегда записывается первая страница.

import requests
from bs4 import BeautifulSoup
import csv


def get_data(url):
    headers = {
        "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/93.0.4577.82 Safari/537.36"
    }
    req = requests.get(url, headers = headers)
    with open("index.html", 'w', encoding="utf-8") as file:
        file.write(req.text)
    with open("index.html", "r", encoding='utf-8') as file:
        src = file.read()
    arr = []
    soup = BeautifulSoup(src, "lxml")
    all_links = soup.find_all('a', class_ = 'market_listing_row_link')
    for link in all_links:
        arr.append(link.get("href"))
        arr.append(link.find("span", class_ = "market_listing_item_name").text)
        arr.append(link.find("span", class_ = "market_listing_game_name").text)
        arr.append(link.find("span", class_ = "market_table_value normal_price").find('span', class_= "normal_price").text)
        arr.append("  ")
    with open("links.csv", "w") as file:
        csv_writer = csv.writer(file)
        for links in arr:
            csv_writer.writerow([links])

for page in range(1, 4):
    url = f"https://steamcommunity.com/market/search?q=&category_570_Hero%5B%5D=any&category_570_Slot%5B%5D=any&category_570_Type%5B%5D=any&appid=570#p{page}_popular_desc"
    get_data(url)

Ответы (1 шт):

Автор решения: handowl
from requests_html import HTMLSession
from bs4 import BeautifulSoup
import csv


def get_data(url):
    session = HTMLSession()
    req = session.get(url)
    req.html.render()
    arr = []
    soup = BeautifulSoup(req.html.html, "lxml")
    all_links = soup.find_all('a', class_ = 'market_listing_row_link')
    for link in all_links:
        arr.append(link.get("href"))
        arr.append(link.find("span", class_ = "market_listing_item_name").text)
        arr.append(link.find("span", class_ = "market_listing_game_name").text)
        arr.append(link.find("span", class_ = "market_table_value normal_price").find('span', class_= "normal_price").text)
        arr.append("  ")
    #UPD: для добавления вместо перезаписи можно использовать флаг "а"
    with open("links.csv", "a") as file:
        csv_writer = csv.writer(file)
        for links in arr:
            csv_writer.writerow([links])

for page in range(1, 4):
    url = f"https://steamcommunity.com/market/search?q=&category_570_Hero%5B%5D=any&category_570_Slot%5B%5D=any&category_570_Type%5B%5D=any&appid=570#p{page}_popular_desc"
    get_data(url)

Все потому что на странице скорее всего js, который подгружает новый список. Если вы перейдете на третью страницу в браузере, вы увидите, что сначала загрузилась первая, а потом js подгружает третью.

Здесь используется другая библиотека requests-html, у объекта класса HTMLSession есть метод render, который позволяет как раз загрузить динамический контент. У этого метода можно передавать кейворд sleep со значением в секундах, так будет подольше, но вероятнее, что точно получите свои данные.

Еще можно создавать только одну сессию вне функции и использовать константно, но у меня не получилось, видимо, не лохи valve)

→ Ссылка