我正在尝试从网站上抓取所有文章链接,而我是否成功做到了。
站点页面上有一个Show more
按钮,用于加载更多文章。
我正在使用Selenium单击此按钮,该按钮也有效。
问题在于单击Show more
不会更改页面的URL,因此,我只能抓取默认显示的初始链接。
这是代码片段:
def startWebDriver():
global driver
options = Options()
options.add_argument("--disable-extensions")
driver = webdriver.Chrome(executable_path = '/home/Downloads/chromedriver_linux64/chromedriver',options=options)
startWebDriver()
count = 0
s = set()
driver.get('https://www.nytimes.com/search? endDate=20181231&query=trump&sort=best&startDate=20180101')
time.sleep(4)
element = driver.find_element_by_xpath('//*[@id="site-content"]/div/div/div[2]/div[2]/div/button')
while(count < 10):
element.click()
time.sleep(4)
count=count+1
url = driver.current_url
我希望在单击Show More
10次后将所有文章链接显示在页面上
答案 0 :(得分:0)
似乎您的目标资源为我们的文章提供了一个不错的API。
使用它代替硒会容易得多。
您可以在Chrome中打开该页面。然后打开开发工具->网络。单击“显示更多”,您可以看到名为v2的API请求(看起来像是GraphQL网关)。
类似
{
"operationName":"SearchRootQuery",
"variables":{
"first":10,
"sort":"best",
"beginDate":"20180101",
"endDate":"20181231",
"text":"trump" ...
}}
您可以模仿该请求,但可以根据需要询问尽可能多的“第一”文章。
编辑:
您可以右键单击DevTools并选择“复制为cURL”。然后将其粘贴到您的终端。这样您就可以了解其工作原理。
之后,您可以使用requests之类的库通过代码进行操作。
答案 1 :(得分:0)
这是使用API信息的POST请求的模拟,正如我在“网络”标签中看到的那样。我已经剥离了似乎是必需的标题。
import requests
url = 'https://samizdat-graphql.nytimes.com/graphql/v2'
headers = {
'nyt-app-type': 'project-vi',
'nyt-app-version': '0.0.3',
'nyt-token': 'MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAlYOpRoYg5X01qAqNyBDM32EI/E77nkFzd2rrVjhdi/VAZfBIrPayyYykIIN+d5GMImm3wg6CmTTkBo7ixmwd7Xv24QSDpjuX0gQ1eqxOEWZ0FHWZWkh4jfLcwqkgKmfHJuvOctEiE/Wic5Qrle323SMDKF8sAqClv8VKA8hyrXHbPDAlAaxq3EPOGjJqpHEdWNVg2S0pN62NSmSudT/ap/BqZf7FqsI2cUxv2mUKzmyy+rYwbhd8TRgj1kFprNOaldrluO4dXjubJIY4qEyJY5Dc/F03sGED4AiGBPVYtPh8zscG64yJJ9Njs1ReyUCSX4jYmxoZOnO+6GfXE0s2xQIDAQAB'
}
data = '''
{"operationName":"SearchRootQuery","variables":{"first":10,"sort":"best","beginDate":"20180101","text":"trump","cursor":"YXJyYXljb25uZWN0aW9uOjk="},"extensions":{"persistedQuery":{"version":1,"sha256Hash":"d2895d5a5d686528b9b548f018d7d0c64351ad644fa838384d94c35c585db813"}}}
'''
with requests.Session() as r:
re = r.post(url, headers = headers, data = data)
print(re.json())
答案 2 :(得分:0)
要从URL中刮取所有文章链接,即Rinkeby的href
属性,请单击以下文本链接,显示更多,您可以使用以下解决方案:
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 selenium.common.exceptions import TimeoutException
options = webdriver.ChromeOptions()
options.add_argument("start-maximized")
options.add_argument('disable-infobars')
driver = webdriver.Chrome(chrome_options=options, executable_path=r'C:\Utility\BrowserDrivers\chromedriver.exe')
driver.get("https://www.nytimes.com/search?%20endDate=20181231&query=trump&sort=best&startDate=20180101")
myLength = len(WebDriverWait(driver, 20).until(EC.visibility_of_all_elements_located((By.XPATH, "//main[@id='site-content']//figure[@class='css-rninck toneNews']//following::a[1]"))))
while True:
driver.execute_script("window.scrollTo(0, document.body.scrollHeight);")
try:
WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.XPATH, "//button[text()='Show More']"))).click()
WebDriverWait(driver, 20).until(lambda driver: len(driver.find_elements_by_xpath("//main[@id='site-content']//figure[@class='css-rninck toneNews']//following::a[1]")) > myLength)
titles = driver.find_elements_by_xpath("//main[@id='site-content']//figure[@class='css-rninck toneNews']//following::a[1]")
myLength = len(titles)
except TimeoutException:
break
for title in titles:
print(title.get_attribute("href"))
driver.quit()