【问题标题】:Can't scrape some static image links from a webpage using requests无法使用请求从网页中抓取一些静态图片链接
【发布时间】:2020-12-25 07:20:36
【问题描述】:

我正在尝试从网站的着陆页中抓取图像。所有图像都在search_results 类名内。当我运行下面的脚本时,我没有得到任何结果。我检查了status_code,发现脚本正在获取403

website link

由于图像是静态的并且在页面源中可用,我如何使用请求抓取图像链接?

import requests
from bs4 import BeautifulSoup

url = 'https://pixabay.com/images/search/office/'

headers = {
    'User-Agent':'Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/85.0.4183.83 Safari/537.36',
}

r = requests.get(url,headers=headers)
print(r.status_code)
soup = BeautifulSoup(r.text,"lxml")
for item in soup.select(".search_results a > img[src]"):
    print(item.get("src"))

与任何浏览器模拟器相关的任何解决方案,例如 selenium,都不是我想要的。

【问题讨论】:

  • HTTP 403 错误意味着服务器不想与您交谈。也许它认为你是一个机器人(你是)。
  • 非常有用的评论@John Gordon。谢谢。
  • 还有其他问题 - 此页面使用 JavaScript 添加项目(在 Web 浏览器中关闭 JavaScript 并检查您的 url)但 requestsBeautifulSoup 无法运行 JavaScript。即使您获得状态200,您也无法获得图像。你可能需要Selenium`来控制可以运行JavaScript的网络浏览器
  • 如果您显示r.text,那么您会看到包含有关 CAPTCHA 信息的 HTML。还有消息Please turn JavaScript on and reload the page.Please enable Cookies. 这可以解释问题403 - 它使用JavaScript 和Cookies 来检查它是否是真正的网络浏览器。

标签: python python-3.x web-scraping python-requests


【解决方案1】:

此页面使用JavaScriptCookies,这会产生问题。它还检查其他标头,不仅是User-Agent

首先:您必须使用requests.Session() 来保存cookie。第二:您必须加载一些页面(即主页)才能获取这些 cookie。当您拥有 cookie 时,它​​将接受其他 URL。第三:它还会检查其他标头以发送 cookie。

我在浏览器中运行页面并在 Chrome/Firefox 中使用 DevTools 复制真实浏览器使用的所有标头,然后我开始测试具有不同标头的请求。最后我发现它需要

headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/85.0.4183.83 Safari/537.36',
    'Accept-Language': 'en-US;q=0.7,en;q=0.3',
    'Cache-Control': 'no-cache',
}

其他问题是页面使用JavaScript 加载图像时滚动页面(“延迟加载”)和一些网址不在scr 但在data-lazy 然后src'blank.gif'


import requests
from bs4 import BeautifulSoup

headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/85.0.4183.83 Safari/537.36',
    #"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8",
    #"Accept-Encoding": "gzip, deflate, br",
    "Accept-Language": "en-US;q=0.7,en;q=0.3",
    "Cache-Control": "no-cache",
    #"Connection": "keep-alive",
    #"Pragma": "no-cache",
}

s = requests.Session()
s.headers.update(headers)  # it will use there hearders in all requests

# --- get cookies ---

url = 'https://pixabay.com/'

r = s.get(url)
print(r.status_code)  # 403 but it is not problem

# only for test 
#r = s.get(url)
#print(r.status_code)  # 200 because it already have cookies

# --- get images ---

url = 'https://pixabay.com/images/search/office/'

r = s.get(url)
print(r.status_code)
#print(r.text)

results = []

soup = BeautifulSoup(r.text, "lxml")

for item in soup.select(".search_results a > img[src]"):
    src = item.get("src")
    if src is not None and 'blank.gif' not in src:
        print('src:', src)
        results.append(src)
    else:
        src = item.get("data-lazy")
        print('data-lazy:', src)
        results.append(src)

print('len:', len(results))

【讨论】:

  • 感谢@furas 提供的宝贵信息。对此,我真的非常感激。就我而言,我仍然得到 403。
  • 您是完全运行我的代码还是对自己的代码进行了更改?您是否在所有请求中都使用了Session?它将保留 cookie 并在所有请求中使用它们。您是否将所有标题添加到 Session ?这样,所有请求都将使用所有这些标头。您可以尝试添加其他标题。在我的示例中,我总是在第一个请求中得到 403 - 因为它还没有 cookie。但是下一个请求已经有 cookie 并且它得到状态200。但是如果我删除一些标题,那么它也会得到403
  • 我完全尝试过the way 你的建议。这是我得到403,403,len: 0 的结果。谢谢。
  • 我也收到了403, 403, len: 0。我们都疯了。
  • 我检查了你的代码,它对我有用。也许服务器出于某种原因不喜欢你。服务器可能有其他方法来控制用户。如果您在短时间内运行许多请求,那么它可能会将其视为机器人并阻止它。或者您的 IP 在黑名单上,它会阻止它。您可以尝试使用一些代理服务器来发送具有不同 IP 的每个请求。但是免费的代理服务器通常是没用的——它们不起作用,或者它们可能被列入黑名单并被屏蔽。
【解决方案2】:

看起来,Pixabay 正在使用 Cloudflare 的 Web 应用程序防火墙 (WAF) 或类似产品。手动解决这个问题非常乏味。

cloudflare-scrape 是一个可以提供帮助的库:https://github.com/Anorov/cloudflare-scrape

【讨论】:

    【解决方案3】:

    这使用Selenium。但是,由于某种原因,它似乎没有在无头模式下找到图像:

    from selenium import webdriver
    from bs4 import BeautifulSoup
    
    
    options = webdriver.ChromeOptions()
    #options.add_argument("headless")
    options.add_experimental_option('excludeSwitches', ['enable-logging'])
    driver = webdriver.Chrome(options=options)
    try:
        driver.implicitly_wait(3)
        driver.get('https://pixabay.com/images/search/office')
        images = driver.find_elements_by_css_selector('.search_results a > img[src]') # wait for images to show up
        soup = BeautifulSoup(driver.page_source, 'lxml')
        for item in soup.select(".search_results a > img[src]"):
            print(item.get("src"))
    finally:
        driver.quit()
    

    打印:

    https://cdn.pixabay.com/photo/2016/03/09/09/22/workplace-1245776__340.jpg
    https://cdn.pixabay.com/photo/2015/01/08/18/26/write-593333__340.jpg
    https://cdn.pixabay.com/photo/2015/02/02/11/09/office-620822__340.jpg
    https://cdn.pixabay.com/photo/2014/05/02/21/50/home-office-336378__340.jpg
    https://cdn.pixabay.com/photo/2016/02/19/11/19/office-1209640__340.jpg
    https://cdn.pixabay.com/photo/2015/02/02/11/08/office-620817__340.jpg
    https://cdn.pixabay.com/photo/2016/03/26/13/09/cup-of-coffee-1280537__340.jpg
    https://cdn.pixabay.com/photo/2017/05/11/11/15/workplace-2303851__340.jpg
    https://cdn.pixabay.com/photo/2015/01/09/11/08/startup-594090__340.jpg
    https://cdn.pixabay.com/photo/2015/01/08/18/25/startup-593327__340.jpg
    https://cdn.pixabay.com/photo/2015/01/08/18/27/startup-593341__340.jpg
    https://cdn.pixabay.com/photo/2014/05/02/21/49/home-office-336373__340.jpg
    https://cdn.pixabay.com/photo/2015/01/09/11/11/office-594132__340.jpg
    https://cdn.pixabay.com/photo/2017/05/04/16/37/meeting-2284501__340.jpg
    https://cdn.pixabay.com/photo/2014/05/03/01/03/macbook-336704__340.jpg
    https://cdn.pixabay.com/photo/2018/01/11/21/27/desk-3076954__340.jpg
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    /static/img/blank.gif
    

    【讨论】:

      猜你喜欢
      • 2021-04-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-09-13
      • 2018-05-14
      • 2015-06-24
      • 1970-01-01
      相关资源
      最近更新 更多