在 Python 中使用 Beautiful Soup 在线检查产品的可用性

Posted

技术标签:

【中文标题】在 Python 中使用 Beautiful Soup 在线检查产品的可用性【英文标题】:Using Beautiful Soup in Python to check availability of a product online 【发布时间】:2017-05-13 10:00:56 【问题描述】:

我正在使用 Python 2.7 和 Beautiful Soup 4.5.1 版

我正在努力使这个非常简单的脚本工作。我的目标是通过解析产品页面的 html 并在

<div class="status online-availability-status">             Sold out online     </div>

这是我第一次使用 Beautiful Soup 模块,如果我遗漏了一些明显的东西,请原谅我。这是我编写的用于获取上述信息的脚本:

import requests
from bs4 import BeautifulSoup

page = requests.get('http://www.bestbuy.ca/en-CA/product/nintendo-nintendo-entertainment-system-nes-classic-edition-console-clvsnesa/10488665.aspx?path=922de2a5ceb066b0f058cc567ad3d547en02')

soup = BeautifulSoup(page.content, 'html.parser')

avail = soup.findAll('div', "class": "status online-availability-status")

但后来我得到了avail 的空列表。知道为什么吗?

非常感谢任何帮助。

【问题讨论】:

你确定你得到了这个页面并且它包含了所需的 div 吗? 可能与页面的加载方式有关:尝试手动加载时首先显示进度条,而页面执行后台查询以检查库存,然后显示“在线售罄”。这意味着在加载原始页面时,该内容不存在。 @Nurzhan 是的,我确定。我现在正在查看页面的元素,它就在那里。 div 实际上有两个类。在这种情况下,您需要将数组传递给选择器:'class': ['status', 'online-availability-status'],或者直接丢弃第一个类 @VBB 感谢您的评论。有关如何解决此问题的任何建议? 【参考方案1】:

如果您尝试打印soup,您会看到它可能会返回类似Access Denied 的内容。这是因为百思买需要一个允许的User-Agent 才能发出 GET 请求。由于您没有在 Header 中指定 User-Agent,因此它不会返回任何内容。

这是生成用户代理的链接 How to use Python requests to fake a browser visit a.k.a and generate User Agent?

或者您可以找出您在自己的浏览器中查看网页时生成的用户代理 https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/User-Agent

【讨论】:

【参考方案2】:

可用性以 JSON 格式加载。您甚至不需要为此解析 HTML:

import urllib
import simplejson

sku = 1048865  # look at the URL of the web page, it is <blablah>//10488665.aspx
# chnage locations to get the right store
response = urllib.urlopen('http://api.bestbuy.ca/availability/products?callback=apiAvailability&accept-language=en&skus=%s&accept=application%2Fvnd.bestbuy.standardproduct.v1%2Bjson&postalCode=M5G2C3&locations=977%7C203%7C931%7C62%7C617&maxlos=3'%sku)
availability = simplejson.loads(response.read())
print availability[0]['shipping']['status']

【讨论】:

谢谢。这会检查商店的可用性吗?我对在线可用性特别感兴趣。 @PollPenn 是的,它就是这样做的【参考方案3】:

正如上面的 cmets 所暗示的,您似乎正在寻找一个由 javascript 在客户端生成的标签;它在加载的页面上使用“检查”显示,但在查看页面源时不显示,这是对请求的调用正在撤回的内容。您可以尝试使用dryscrape(可能需要使用pip install dryscrape 安装)。

import dryscrape
from bs4 import BeautifulSoup
session = dryscrape.Session()
url = 'http://www.bestbuy.ca/en-CA/product/nintendo-nintendo-entertainment-system-nes-classic-edition-console-clvsnesa/10488665.aspx?path=922de2a5ceb066b0f058cc567ad3d547en02'
session.visit(url)
response = session.body()
soup = BeautifulSoup(response)
avail = soup.findAll('div', "class": "status online-availability-status")

这是与抓取动态生成的内容相关的问题中最流行的解决方案:

Web-scraping JavaScript page with Python

【讨论】:

以上是关于在 Python 中使用 Beautiful Soup 在线检查产品的可用性的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Beautiful Soup 4 (Python) 中使用搜索栏

在 Python 中使用 Beautiful Soup 在线检查产品的可用性

python 使用Beautiful Soup从页面中提取数据

使用python beautiful soup或html模块的电子邮件刮刀

如何使用 Python 和 Beautiful Soup 从框架中抓取信息

Python爬虫编程思想(52):使用Beautiful Soup选择子节点