我正在尝试获取餐厅的链接,但我只能获取前 30 家餐厅的链接,而无法获取所有其他餐厅的链接。 马德里地区的餐馆有数百家,分页每页只显示 30 家,以下代码只获取这 30 家
import re
import requests
from openpyxl import Workbook
from bs4 import BeautifulSoup as b
city_name = 'Madrid'
geo_code = '187514'
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36"
}
data = requests.get(
"https://www.tripadvisor.com//Restaurants-g{}-{}.html".format(geo_code, city_name), headers=headers
).text
for link in re.findall(r'"detailPageUrl":"(.*?)"', data):
print("https://www.tripadvisor.com.sg/" + link)
next_link = "https://www.tripadvisor.com.sg/" + link
f.write('%s\n' % next_link)
你说的没错!问题在于 TripAdvisor 通过 JavaScript 动态加载分页内容,而你的代码目前只抓取了初始页面。
为了获取所有餐厅链接,你需要模拟分页的行为并依次访问每一页。这里有两种主要的方法:
方法一:分析并请求 TripAdvisor 的 API
TripAdvisor 使用 API 来加载分页数据。你可以通过浏览器开发者工具(Network 标签)观察网络请求,找到相应的 API URL。
一般来说,API 的 URL 会包含页码、排序方式等参数。你需要分析这些参数的规律,然后使用循环结构依次请求每一页的数据,直到获取所有餐厅链接。
这种方法的优点是效率高,缺点是需要分析 API 的参数结构,如果 TripAdvisor 修改了 API,你的代码可能需要调整。
方法二:使用 Selenium 或 Playwright 等浏览器自动化工具
Selenium 和 Playwright 可以模拟真实用户的浏览器行为,包括点击分页按钮、滚动页面等。你可以使用这些工具加载每一页的内容,然后使用 BeautifulSoup 解析餐厅链接。
以下是使用 Selenium 的示例代码:
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from bs4 import BeautifulSoup
city_name = 'Madrid'
geo_code = '187514'
# 使用 Chrome 浏览器
driver = webdriver.Chrome()
# 替换为你的 ChromeDriver 路径: driver = webdriver.Chrome(executable_path="/path/to/chromedriver")
url = f"https://www.tripadvisor.com//Restaurants-g{geo_code}-{city_name}.html"
driver.get(url)
while True:
# 等待页面加载完成
WebDriverWait(driver, 10).until(EC.presence_of_element_located((By.CLASS_NAME, 'pageNumbers')))
# 使用 BeautifulSoup 解析当前页面的餐厅链接
soup = BeautifulSoup(driver.page_source, 'html.parser')
for link in soup.find_all('a', {'class': 'bGoCa'}): # 根据实际情况修改 class 名称
print(link['href'])
# 查找下一页按钮
try:
next_button = driver.find_element(By.XPATH, "//a[@class='nav next rndBtn ui_button primary taLnk'][contains(., 'Next')]") # 根据实际情况修改 XPath
next_button.click()
except:
# 没有找到下一页按钮,说明已经到达最后一页
break
driver.quit()
这种方法的优点是不需要分析 API,代码更简洁易懂。缺点是效率较低,因为需要加载完整的网页内容。
你需要根据实际情况选择适合你的方法,并根据 TripAdvisor 网站的结构调整代码。
标签:python,web-scraping,beautifulsoup,tripadvisor From: 75316907