【问题标题】:Retrieving an image gives 403 error while it works with browser使用浏览器检索图像时出现 403 错误
【发布时间】:2022-01-26 16:32:14
【问题描述】:

您好,我正在尝试构建一个漫画下载器应用程序,因此我正在抓取几个网站,但是一旦我获得图像 URL,我就会遇到问题。 我可以使用我的浏览器 (chrome) 查看图像,我也可以下载它,但是我无法使用任何流行的脚本库来做同样的事情。

这是我尝试过的:

String imgSrc = "https://cdn.mangaeden.com/mangasimg/aa/aa75d306397d1d11d07d66746dae78a36dc78672ae9e97a08cb7abb4.jpg"
Connection.Response resultImageResponse = Jsoup.connect(imgSrc)
                    .userAgent(
                            "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/535.21 (KHTML, like Gecko) Chrome/19.0.1042.0 Safari/535.21")
                    .referrer("none").execute();

// output here
OutputStreamWriter out = new OutputStreamWriter(new FileOutputStream(new java.io.File(String.valueOf(imgPath))));
out.write(resultImageResponse.body());          // resultImageResponse.body() is where the image's contents are.
out.close();

我也试过这个:

URL imgUrl = new URL(imgSrc);
Files.copy(imgUrl.openStream(), imgPath);

最后,由于我确定链接有效,因此我尝试使用 python 下载图像,但在这种情况下,我也会收到 403 错误

import requests
base_url = "https://cdn.mangaeden.com/mangasimg/d0/d08f07d762acda8a1f004677ab2414b9766a616e20bd92de4e2e44f1.jpg"
res = requests.get(url)

谷歌搜索我发现这个Unable to get image url in Mangaeden API Angular 6 似乎真的很接近我的问题,但是我不明白我是否设置了错误的推荐人或者它根本不起作用......

你有什么建议吗? 谢谢!

【问题讨论】:

  • curl.exe "https://cdn.mangaeden.com/mangasimg/d0/d08f07d762acda8a1f004677ab2414b9766a616e20bd92de4e2e44f1.jpg" 给出错误代码:1020(cloudflare 拒绝访问),所以可能有一些缓存或 cookie 令牌保护
  • 将 URL 直接粘贴到浏览器中也会出现 403(使用 Chrome 和使用 Postman)。
  • 嗯,我认为是正常的 Postman/curl 不起作用,当配置相同时,它们与请求库完全相同。我的问题是:为什么浏览器可以显示图像?它有一些不同的配置吗? @BrokenBenchmark
  • 抱歉,我应该澄清一下我同时使用了 Chrome 和 Postman。
  • 哦...这出乎意料,为什么我会看到这张图片?我尝试使用不同的浏览器和设备打开链接,并且效果很好。 IE。我将相同的链接发送到我的手机,然后点击它

标签: python java beautifulsoup python-requests jsoup


【解决方案1】:

如何解决?

在您的请求中添加一些“标题”以表明您可能是“浏览器”,这将为您提供 200 作为响应,您可以保存文件。

注意 这也适用于邮递员,只需覆盖隐藏的用户代理,您就会得到图像作为响应

示例(python)

import requests
headers ={
    'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.114 Safari/537.36'
}
url = "https://cdn.mangaeden.com/mangasimg/d0/d08f07d762acda8a1f004677ab2414b9766a616e20bd92de4e2e44f1.jpg"
res = requests.get(url,headers=headers)
with open("image.jpg", 'wb') as f:
        f.write(res.content)

【讨论】:

    【解决方案2】:

    有人写了这个答案,但后来把它删除了,所以我会复制答案以防万一。

    AFAIK,除了 HTML 文档之外,您无法下载任何其他内容 使用 jsoup。

    如果你在浏览器上打开开发者工具,你可以得到确切的 浏览器发出的请求。使用 Chrome,就是这样。

    在您的情况下,最小的 cURL 请求是:

    'https://cdn.mangaeden.com/mangasimg/aa/aa75d306397d1d11d07d66746dae78a36dc78672ae9e97a08cb7abb4.jpg'
    \   -H 'user-agent: Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/535.21
    (KHTML, like Gecko) Chrome/19.0.1042.0 Safari/535.21' \   --output
    image.jpg;
    

    您可以参考 HedgeHog 的示例 Python 的答案 解决方案;这是使用新 HTTP 在 Java 中实现相同目标的方法 客户:

    import java.net.URI; import java.net.http.HttpClient; import
    java.net.http.HttpRequest; import
    java.net.http.HttpResponse.BodyHandlers; import java.nio.file.Path;
    import java.nio.file.Paths;
    
    public class ImageDownload {
        public static void main(String[] args) throws Exception {
            HttpClient client = HttpClient.newHttpClient();
            HttpRequest request = HttpRequest.newBuilder()
                .uri(URI.create("https://cdn.mangaeden.com/mangasimg/aa/aa75d306397d1d11d07d66746dae78a36dc78672ae9e97a08cb7abb4.jpg"))
                .header("user-agent", "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/535.21 (KHTML, like Gecko) Chrome/19.0.1042.0
    Safari/535.21")
                .build();
            client.send(request, BodyHandlers.ofFile(Paths.get("image.jpg")));
        } }
    

    我在我的 java 代码中采用了这个解决方案。 另外,最后一点,如果图像已下载但您无法打开它,可能是由于请求中的 503 错误代码,在这种情况下您只需要再次执行请求即可。您可以识别损坏的图像,因为图像阅读器会说类似

    不是 JPEG 文件:以 0x3c 0x68 开头

    这是<h,一个HTML错误页面而不是图片

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-01-29
      • 1970-01-01
      • 1970-01-01
      • 2015-11-23
      • 1970-01-01
      • 1970-01-01
      • 2016-05-08
      相关资源
      最近更新 更多