使用 Python 3 从动态 HTML Table 中提取数据

Extract data from dynamic HTML Table with Python 3

我一直在研究 python 3 脚本来生成 BibTeX 条目,并且 ISSN's 我想用它来获取有关相关期刊的信息。

例如,我想获取 ISSN 0897-4756,发现这是 Chemistry of Materials 期刊,由 ACS Publications 出版。

我可以使用 this site 手动执行此操作,其中我要查找的信息存储在 lxml table //table[@id="journal-search-results-table"] 中,或者更具体地说,存储在table 正文。

但是,我无法使用 python 3.x

使其成功自动化

我尝试使用 httplib2requestsurllib2lxml.html 包中的方法访问数据,但迄今为止没有成功。

目前我所拥有的如下所示:

import certifi       
import lxml.html
import urllib.request

ISSN = "0897-4756"
address = "https://www.journalguide.com/journals/search?type=journal-name&journal-name={}".format(ISSN)

hdr = {'User-Agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.64 Safari/537.11',
  'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
  'Accept-Charset': 'ISO-8859-1,utf-8;q=0.7,*;q=0.3',
  'Accept-Encoding': 'none',
  'Accept-Language': 'en-US,en;q=0.8',
  'Connection': 'keep-alive'}

request = urllib.request.Request(address,None,hdr)  #The assembled request
response = urllib.request.urlopen(request)
html = response.read()
tree = lxml.html.fromstring(html)

print(tree.xpath('//table[@id="journal-search-results-table"]/text()'))
# >> ['\n', '\n']
# Shows that I am connecting to the table

print(tree.xpath('//table[@id="journal-search-results-table"]//td/text()'))
# >> []
# Should???? hold the data segments that I am looking for?

Exact page being queryed by the above

据我所知,似乎 table 的 tbody 元素,因此它包含的 trtd 元素不是在 python 解释 HTML 时加载 - 因此我无法读取数据。

如何才能从上面指定的table读出期刊名称和出版商?

正如您在问题中提到的,此 table 动态变化 javascript。要解决这个问题,您实际上必须使用以下方法渲染 javascript

  • selenium 这样的 Web 驱动程序,它以用户看到的方式模拟网站(通过渲染 javascript)
  • requests-html,这是一个相对较新的模块,允许您在网页上呈现 javascript,并且具有许多其他令人惊叹的网络抓取功能

这是使用请求解决问题的一种方法-html:

from requests_html import HTMLSession

ISSN = "0897-4756"
address = "https://www.journalguide.com/journals/search?type=journal-name&journal-name={}".format(ISSN)

hdr = {
    'User-Agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.64 Safari/537.11',
    'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
    'Accept-Charset': 'ISO-8859-1,utf-8;q=0.7,*;q=0.3',
    'Accept-Encoding': 'none',
    'Accept-Language': 'en-US,en;q=0.8',
    'Connection': 'keep-alive'
}

ses = HTMLSession()
response = ses.get(address, headers=hdr)
response.html.render() # render the javascript to load the elements in the table
tree = response.html.lxml # no need to import lxml.html because requests-html can do this for you

print(tree.xpath('//table[@id="journal-search-results-table"]/text()'))
# >> ['\n', '\n']

print(tree.xpath('//table[@id="journal-search-results-table"]//td/text()'))
# >> ['ACS Publications', '1.905', 'No', '\n', '\n', '\n']