动态JS在抓取网站时生成代码

问题描述 投票:3回答:1

我是一个刮痧的新手。我正试图用按钮立即从this site中榨取价值。 我尝试的选项是:

from PyQt4.QtGui import QApplication
from PyQt4.QtCore import QUrl
from PyQt4.QtWebKit import QWebPage

class Client(QWebPage):
    def __init__(self):
        self.app = QApplication(sys.argv)
        QWebPage.__init__(self)
        # self.loadFinished.connect(self.on_page_load)
        # self.mainFrame().load(QUrl(url))
        # self.app.exec_()
    def on_page_load(self):
        self.app.quit()
    def mypage(self, url):
        self.loadFinished.connect(self.on_page_load)
        self.mainFrame().load(QUrl(url))
        self.app.exec_()
client_response = Client()
def parse(url):                # OSRS + RS3
    client_response.mypage(url)
    source = client_response.mainFrame().toHtml()
    soup = BeautifulSoup(source, 'html.parser')
    osrs_text = soup.findAll('input', attrs={'type': 'number'})
    quantity = (osrs_text[0])['min']
    final = 0
    if(quantity == '1'):
        final_osrs = round(float(soup.findAll('span', attrs={'id':'goldprice'})[0].text),3)
        print(final_osrs)

    else:
        price = round(float(soup.findAll('span', attrs={'id':'goldprice'})[0].text),3)
        final_rs3 = price/int(quantity)
        print(final_rs3)

这种方法并不好,因为它需要花费太多时间来刮擦。我也尝试过Selenium Approach,但目前也不需要。 你们能告诉我更好的方法吗? Here is what I need。任何帮助将非常感谢。谢谢。

P.S:我试过这个库,因为内容是动态生成的。

python python-3.x web web-scraping beautifulsoup
1个回答
3
投票

我不确定您将获得多少性能差异,但您可以尝试检查此解决方案。

import requests
from bs4 import BeautifulSoup

baseUrl = 'https://www.rsmalls.com/osrs-gold'
postUrl = 'https://www.rsmalls.com/index.php?route=common/quickbuy/rsdetail'

with requests.Session() as session:
    res = session.get(baseUrl)
    soup = BeautifulSoup(res.text, 'lxml')
    game_id = soup.select_one("#choose-game > option[selected]")['value']
    response = session.post(postUrl, data={'game_id': game_id}).json()
    print(f"{'Gold Price:'} {response['price']}")

在此代码中,首先我获得了“Runescape 2007”的ID,以防网站所有者更改它。如果您确定它不会改变,您可以跳过该步骤直接提供值'345'作为下一个帖子请求的ID。

如前所述,价格加载了JS代码。使用浏览器开发工具,我可以获得实际的POST请求来获取价格,这需要从下拉列表中选择ID。对https://www.rsmalls.com/index.php?route=common/quickbuy/rsdetail的POST请求给出了一个json响应:

{"success":true,"product_id":"30730","price":0.85,"server_id":"1661","server_option":"463","quantity":"1|5|10|20|50|100|200|300|500|1000|1500|2000","name":"M"}

所以,我已经将响应解析为json并从中获得了价格。 如果您有任何疑问,请告诉我。

编辑:

https://rsmalls.com/runescape3-gold上有不同的POST请求,因此相同的解决方案不起作用。每个页面/网站/数据的POST请求可以不同。你可以使用浏览器devtools找到这样的帖子请求,如下所示。在右侧,您可以看到对URL的POST请求,在底部您还可以找到发送到POST请求的数据。另请注意,在对此请求的响应中,它始终以1个单位的价格回复,因此如果网站上的默认单位数大于1(如下面的截图中的5个),则可能不匹配。

enter image description here

© www.soinside.com 2019 - 2024. All rights reserved.