python 网页抓取谷歌航班价格

oalqel3c  于 2023-03-28  发布在  Python
关注(0)|答案(4)|浏览(154)

我试图学习使用Python库BeautifulSoup,我想,例如,在Google Flights上刮一个航班的价格。所以我连接到Google Flights,例如在这个链接,我想得到最便宜的航班价格。
因此,我将使用类“gws-flights-results__routinary-price”获取div中的值(如图所示)。

下面是我写的简单代码:

from bs4 import BeautifulSoup
import urllib.request

url = 'https://www.google.com/flights?hl=it#flt=/m/07_pf./m/05qtj.2019-04-27;c:EUR;e:1;sd:1;t:f;tt:o'
page = urllib.request.urlopen(url)
soup = BeautifulSoup(page, 'html.parser')
div = soup.find('div', attrs={'class': 'gws-flights-results__itinerary-price'})

但是生成的div具有类NoneType
我也试着

find_all('div')

但是在我用这种方法找到的所有div中,没有我感兴趣的div。有人能帮助我吗?

ekqde3dh

ekqde3dh1#

看起来JavaScript需要运行,所以使用像Selenium这样的方法

from selenium import webdriver
url = 'https://www.google.com/flights?hl=it#flt=/m/07_pf./m/05qtj.2019-04-27;c:EUR;e:1;sd:1;t:f;tt:o'
driver = webdriver.Chrome()
driver.get(url)
print(driver.find_element_by_css_selector('.gws-flights-results__cheapest-price').text)
driver.quit()
8gsdolmq

8gsdolmq2#

你正在学习网页抓取,这是一件好事!你得到NoneType的原因是因为你正在抓取的网站动态加载内容。当请求库获取URL时,它只包含javascript。而这个类的div“gws-flights-results__iterary-price”还没有呈现!所以你使用的抓取方法不可能抓取这个网站。

  • 但是,您可以使用其他方法,例如使用selenium或splash等工具获取页面以呈现JavaScript,然后解析内容。*
irtuqstp

irtuqstp3#

BeautifulSoup是提取HTML或XML部分内容的一个很好的工具,但在这里,您似乎只需要获取JSON对象的另一个GET请求的URL。
(我现在不在电脑旁,明天可以用例子更新。)

ua4mk5z4

ua4mk5z44#

没有seleniumBeautifulsoup将无法工作,因为数据是动态呈现的。
要查看和解析所有结果,可以使用显示show more按钮的click pagination:

button = driver.find_element(By.CSS_SELECTOR, ".XsapA")
driver.execute_script("arguments[0].click();", button)

您可以使用SelectorGadget Chrome扩展在页面上定义CSS选择器。
检查online IDE中的代码。

import time, json, lxml
from selenium import webdriver
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.common.by import By
from bs4 import BeautifulSoup

URL = "https://www.google.com/travel/flights/search?tfs=CBwQAhooagwIAxIIL20vMDdfcGYSCjIwMjMtMDQtMDZyDAgDEggvbS8wNXF0ahooagwIAxIIL20vMDVxdGoSCjIwMjMtMDQtMTByDAgDEggvbS8wN19wZnABggELCP___________wFAAUgBmAEB&hl=it"

service = Service(executable_path="chromedriver")
options = webdriver.ChromeOptions()
options.add_argument("--headless")
options.add_argument("--lang=en")
options.add_argument("user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36")
options.add_argument("--no-sandbox")
options.add_argument("--disable-dev-shm-usage")
driver = webdriver.Chrome(service=service, options=options)

driver.get(URL)
time.sleep(1)
button = driver.find_element(By.CSS_SELECTOR, ".XsapA")
driver.execute_script("arguments[0].click();", button)
driver.execute_script("window.scrollTo(0, document.body.scrollHeight);")
time.sleep(5)

soup = BeautifulSoup(driver.page_source, 'lxml')
driver.quit()

data = []

for flight in soup.select(".yR1fYc"):
    name = flight.select_one(".Ir0Voe .sSHqwe span").text
    price = flight.select_one(".FpEdX span").text
    
    data.append({
        "name": name,
        "price": price
    })
print(json.dumps(data, indent=2, ensure_ascii=False))

输出示例:

[
  {
    "name": "Vueling",
    "price": "707 USD"
  },
  {
    "name": "Vueling",
    "price": "707 USD"
  },
  {
    "name": "Vueling",
    "price": "707 USD"
  },
  other results ...
]

如果你想了解更多关于网站抓取的信息,可以阅读13 ways to scrape any public data from any website博客文章。

相关问题