使用 Python 从网站下载所有 pdf 文件

     2023-02-23     14

关键词:

【中文标题】使用 Python 从网站下载所有 pdf 文件【英文标题】:Download all pdf files from a website using Python 【发布时间】:2019-07-04 03:01:02 【问题描述】:

我遵循了几个在线指南,试图构建一个脚本,该脚本可以识别和下载网站上的所有 pdf,从而使我免于手动操作。到目前为止,这是我的代码:

from urllib import request
from bs4 import BeautifulSoup
import re
import os
import urllib

# connect to website and get list of all pdfs
url="http://www.gatsby.ucl.ac.uk/teaching/courses/ml1-2016.html"
response = request.urlopen(url).read()
soup= BeautifulSoup(response, "html.parser")     
links = soup.find_all('a', href=re.compile(r'(.pdf)'))


# clean the pdf link names
url_list = []
for el in links:
    url_list.append(("http://www.gatsby.ucl.ac.uk/teaching/courses/" + el['href']))
#print(url_list)


# download the pdfs to a specified location
for url in url_list:
    print(url)
    fullfilename = os.path.join('E:\webscraping', url.replace("http://www.gatsby.ucl.ac.uk/teaching/courses/ml1-2016/", "").replace(".pdf",""))
    print(fullfilename)
    request.urlretrieve(url, fullfilename)

该代码似乎可以找到所有 pdf(取消注释 print(url_list) 以查看此内容)。但是,它在下载阶段失败。特别是我得到了这个错误,我无法理解出了什么问题:

E:\webscraping>python get_pdfs.py
http://www.gatsby.ucl.ac.uk/teaching/courses/http://www.gatsby.ucl.ac.uk/teaching/courses/ml1-2016/cribsheet.pdf
E:\webscraping\http://www.gatsby.ucl.ac.uk/teaching/courses/cribsheet
Traceback (most recent call last):
  File "get_pdfs.py", line 26, in <module>
    request.urlretrieve(url, fullfilename)
  File "C:\Users\User\Anaconda3\envs\snake\lib\urllib\request.py", line 248, in urlretrieve
    with contextlib.closing(urlopen(url, data)) as fp:
  File "C:\Users\User\Anaconda3\envs\snake\lib\urllib\request.py", line 223, in urlopen
    return opener.open(url, data, timeout)
  File "C:\Users\User\Anaconda3\envs\snake\lib\urllib\request.py", line 532, in open
    response = meth(req, response)
  File "C:\Users\User\Anaconda3\envs\snake\lib\urllib\request.py", line 642, in http_response
    'http', request, response, code, msg, hdrs)
  File "C:\Users\User\Anaconda3\envs\snake\lib\urllib\request.py", line 570, in error
    return self._call_chain(*args)
  File "C:\Users\User\Anaconda3\envs\snake\lib\urllib\request.py", line 504, in _call_chain
    result = func(*args)
  File "C:\Users\User\Anaconda3\envs\snake\lib\urllib\request.py", line 650, in http_error_default
    raise HTTPError(req.full_url, code, msg, hdrs, fp)
urllib.error.HTTPError: HTTP Error 404: Not Found

有人可以帮帮我吗?

【问题讨论】:

【参考方案1】:

查看以下实现。我使用requests 模块而不是urllib 进行下载。此外,我使用.select() 方法而不是.find_all() 来避免使用re

import os
import requests
from urllib.parse import urljoin
from bs4 import BeautifulSoup

url = "http://www.gatsby.ucl.ac.uk/teaching/courses/ml1-2016.html"

#If there is no such folder, the script will create one automatically
folder_location = r'E:\webscraping'
if not os.path.exists(folder_location):os.mkdir(folder_location)

response = requests.get(url)
soup= BeautifulSoup(response.text, "html.parser")     
for link in soup.select("a[href$='.pdf']"):
    #Name the pdf files using the last portion of each link which are unique in this case
    filename = os.path.join(folder_location,link['href'].split('/')[-1])
    with open(filename, 'wb') as f:
        f.write(requests.get(urljoin(url,link['href'])).content)

【讨论】:

谢谢。这是简短而干净的。这是我第一次使用网络爬虫——它通常很慢吗?每个文件需要几秒钟?谢谢。 @SIM,如何以亚洲字符(URL 的一部分)命名下载的 PDF?我看到了这一点,但不确定如何将其放入上述代码中:qiita.com/mix/items/87d094414e46f857de45 @SIM 这适用于提供的链接。我正在另一个页面上尝试,我知道有几个指向 pdf 文档的链接。我只得到 2 个。 嗨,我知道有点晚了,请,我尝试了这个 URL = "covidmaroc.ma/Pages/LESINFOAR.aspx" 上的代码,但它没有工作,我不知道为什么,因为我不熟悉网络抓取,请提供任何帮助。【参考方案2】:

一般来说,上面的答案应该有效。但是,您应该评估您尝试使用的网页的 html 源代码。例如,有些可能在元标记中有 og_url 属性,而有些可能没有。如果您使用的是安全网站(假设您的大学的课程网页),这是可能的。在这种情况下,您必须以不同的方式提取 pdf 链接。

你可以在这里找到一个很好的解释和解决方案:

https://medium.com/@dementorwriter/notesdownloader-use-web-scraping-to-download-all-pdfs-with-python-511ea9f55e48

【讨论】:

【参考方案3】:

几个链接已经包含导致 404 未找到的服务器地址。此外,您不应从文件名中删除 .pdf,因为它会在没有扩展名的情况下保存它。

from urllib import request
from bs4 import BeautifulSoup
import re
import os
import urllib

# connect to website and get list of all pdfs
url="http://www.gatsby.ucl.ac.uk/teaching/courses/ml1-2016.html"
response = request.urlopen(url).read()
soup= BeautifulSoup(response, "html.parser")     
links = soup.find_all('a', href=re.compile(r'(.pdf)'))


# clean the pdf link names
url_list = []
for el in links:
if(el['href'].startswith('http')):
    url_list.append(el['href'])
else:
    url_list.append("http://www.gatsby.ucl.ac.uk/teaching/courses/" + el['href'])

print(url_list)


# download the pdfs to a specified location
for url in url_list:
    print(url)
    fullfilename = os.path.join('E:\webscraping', url.replace("http://www.gatsby.ucl.ac.uk/teaching/courses/ml1-2016/", ""))
    print(fullfilename)
    request.urlretrieve(url, fullfilename)

【讨论】:

这是一个很好的答案。它工作得很好。谢谢。 如果我们提供基本 url,此方法是从网页还是整个网站域下载所有 pdf 文件?【参考方案4】:

我根据@SIM's answer 和附加的argparse 编写了一个新颖的脚本。我的完整代码如下:

import os
import requests
from urllib.parse import urljoin
from bs4 import BeautifulSoup
import argparse

#%% Example
# one pdf
#   python all_pdf_dl.py -l https://memento.epfl.ch/academic-calendar/ --save-here
# many pdfs
#   python all_pdf_dl.py -l https://idsc.ethz.ch/education/lectures/recursive-estimation.html

#%% Functions
def all_pdf_download(args):
    base_url = args.link
    if args.save_here:
        folder_path = os.getcwd()
    else:
        folder_path = args.folder_path
        if not os.path.exists(args.folder_path):os.mkdir(args.folder_path)
    print("====== 1. Set savepath:  ======".format(folder_path))
    print("====== 2. Start searching ======")
    #response = requests.get(base_url)
    response = requests.get(base_url, headers='User-Agent': 'Custom')
    soup= BeautifulSoup(response.text, "html.parser")
    search_res = soup.select("a[href$='.pdf']")
    print(" files found!!!".format(len(search_res)))
    print("====== 3. Start downloading ======")
    for counter, link in enumerate(search_res):
        #Name the pdf files using the last portion of each link which are unique in this case
        filename = link['href'].split('/')[-1]
        file_save_path = os.path.join(folder_path,link['href'].split('/')[-1])
        if args.print_all:
            print("[/] ".format(counter+1, len(search_res), filename))
        with open(file_save_path, 'wb') as f:
            f.write(requests.get(urljoin(base_url,link['href'])).content)
    print("====== 4. Finished!!! ======")

if __name__ == "__main__":
    parser = argparse.ArgumentParser(description='Test argparse')
    ####################################
    ############ ALL OPTION ############
    ## Main option
    # -l/--link
    parser.add_argument('-l', '--link', required=True, type=str,
                        help='write down site name')
    # --print-all
    parser.add_argument('--print-all', dest='print_all', action='store_true',
                        help="print all filename")
    parser.set_defaults(print_all=True)
    # --save-here
    parser.add_argument('--save-here', dest='save_here', action='store_true',
                        help="save files here")
    parser.set_defaults(save_here=False)
    # --save--folder
    # default setting -> Downloads/ in user’s home directory obtained by (os.path.expanduser('~'))
    parser.add_argument('-f', '--folder_path', default=r""+os.path.join(os.path.expanduser('~'), "Downloads"), 
                        type=str, help='save files in the given folder')

    ########################################
    ############ PARSING OPTION ############
    args = parser.parse_args()
    all_pdf_download(args)

更多详情和更新可以参考我的gist-hibetterheyj/all_pdf_dl.py

最好的!

【讨论】:

如果我们提供基本 url,此方法是从网页还是整个网站域下载所有 pdf 文件?

如何在 python 中使用 selenium 下载 pdf 文件

】如何在python中使用selenium下载pdf文件【英文标题】:Howtodownloadpdffilesusingseleniuminpython【发布时间】:2018-11-1314:52:19【问题描述】:我正在尝试使用selenium从网站下载pdf文件,但我能够打开文件,但无法使用代码自动下载。代码... 查看详情

使用 Python 请求模块下载并保存 PDF 文件

】使用Python请求模块下载并保存PDF文件【英文标题】:DownloadandsavePDFfilewithPythonrequestsmodule【发布时间】:2016-04-0221:16:49【问题描述】:我正在尝试从网站下载PDF文件并将其保存到磁盘。我的尝试要么因编码错误而失败,要么导... 查看详情

从 PDF 中提取文本 - 所有页面和输出 - 使用 Python 的文件

】从PDF中提取文本-所有页面和输出-使用Python的文件【英文标题】:ExtractingtextfromaPDF-AllpagesandOutput-fileusingPython【发布时间】:2017-04-1003:28:52【问题描述】:我是Python新手。我正在使用此代码来提取文本。是否可以提取所有页面... 查看详情

如何使用 wget 从网站下载所有文件(但不是 HTML)?

】如何使用wget从网站下载所有文件(但不是HTML)?【英文标题】:Howtodownloadallfiles(butnotHTML)fromawebsiteusingwget?【发布时间】:2012-02-0400:41:16【问题描述】:如何使用wget并从网站获取所有文件?我需要除网页文件以外的所有文件... 查看详情

如何使用 Python 从需要登录信息的网站下载文件?

】如何使用Python从需要登录信息的网站下载文件?【英文标题】:HowtodownloadfilefromwebsitethatrequireslogininformationusingPython?【发布时间】:2014-05-1305:13:24【问题描述】:我正在尝试使用Python从网站下载一些数据。如果您只是复制并粘... 查看详情

使用 python 从 firebase 存储中下载所有文件

】使用python从firebase存储中下载所有文件【英文标题】:Downloadallfilesfromfirebasestorageusingpython【发布时间】:2018-01-1006:34:22【问题描述】:我正在做一个项目,用户将图像上传到Firebase存储中,我想检索所有这些图像并在本地存储... 查看详情

使用 BeautifulSoup 将网站上的所有图像下载到指定文件夹的 Python 脚本

】使用BeautifulSoup将网站上的所有图像下载到指定文件夹的Python脚本【英文标题】:PythonscripttodownloadallimagesfromawebsitetoaspecifiedfolderwithBeautifulSoup【发布时间】:2018-12-0618:09:21【问题描述】:我找到thispost并想稍微修改脚本以将图像... 查看详情

在python中使用PDFMiner从PDF文件中提取文本?

】在python中使用PDFMiner从PDF文件中提取文本?【英文标题】:ExtractingtextfromaPDFfileusingPDFMinerinpython?【发布时间】:2014-12-1702:54:44【问题描述】:我正在寻找有关如何使用PDFMiner和Python从PDF文件中提取文本的文档或示例。看起来PDFMi... 查看详情

如何通过自动下载链接使用 Python 访问 PDF 文件?

】如何通过自动下载链接使用Python访问PDF文件?【英文标题】:HowcanIaccessaPDFfilewithPythonthroughanautomaticdownloadlink?【发布时间】:2021-07-1501:02:38【问题描述】:我正在尝试创建一个自动Python脚本,该脚本可以转到this之类的网页,在... 查看详情

无法使用python从URL下载文件

】无法使用python从URL下载文件【英文标题】:UnabletodownloadfilefromURLusingpython【发布时间】:2022-01-1812:18:43【问题描述】:我正在尝试从URL下载文件:https://www.cmegroup.com/content/dam/cmegroup/notices/clearing/2020/08/Chadv20-239.pdf我尝试使用pytho... 查看详情

浏览pdf文件以查找特定页面并使用python从图像中提取表格数据

】浏览pdf文件以查找特定页面并使用python从图像中提取表格数据【英文标题】:Navigatethroughapdffiletofindspecificpagesandextracttabulardatafromimagewithpython【发布时间】:2022-01-1812:23:44【问题描述】:我遇到了一项任务,该任务要求我通过py... 查看详情

在 Zapier 中使用代码步骤下载 PDF

】在Zapier中使用代码步骤下载PDF【英文标题】:DownloadPDFusingCodestepinZapier【发布时间】:2017-06-2806:14:49【问题描述】:我正在尝试在Zapier的“代码”步骤中使用Javascript从网站下载PDF。我正在努力寻找有关如何输出文件对象的文档... 查看详情

如何从网站获取文本数据并使用python存储为excel文件

】如何从网站获取文本数据并使用python存储为excel文件【英文标题】:howtofetchtextdatafromwebsiteandstoringasexcelfileusingpython【发布时间】:2021-12-2715:42:07【问题描述】:我想创建一个脚本来获取以下网站中的所有数据:https://www.bis.doc.g... 查看详情

如何使用 beautifulSoup 从网站中提取和下载所有图像?

】如何使用beautifulSoup从网站中提取和下载所有图像?【英文标题】:HowtoextractanddownloadallimagesfromawebsiteusingbeautifulSoup?【发布时间】:2013-08-2619:52:54【问题描述】:我正在尝试从url中提取和下载所有图像。我写了一个脚本importurlli... 查看详情

使用 NSURLSessionDownloadTask 从重定向 URL 下载 pdf 文件

】使用NSURLSessionDownloadTask从重定向URL下载pdf文件【英文标题】:DownloadingapdffileusingNSURLSessionDownloadTaskfromredirectURL【发布时间】:2014-11-1713:36:01【问题描述】:我正在制作一个用户登录网站并下载一些pdf文件的应用程序。我能够使... 查看详情

从气候变化网站 PYTHON 抓取文件

...索数据,并且希望在python上完成一组年份。该网站的代码使用“id”而不 查看详情

如何使用python从网站中提取所有链接[重复]

】如何使用python从网站中提取所有链接[重复]【英文标题】:Howtoextractalllinksfromawebsiteusingpython[duplicate]【发布时间】:2021-07-2110:14:06【问题描述】:我编写了一个脚本来从网站中提取链接,效果很好这是源代码importrequestsfrombs4impo... 查看详情

从应用程序下载 PDF 不适用于 Android 11

...在我的应用程序中下载PDF并在PDF查看器中显示它。我没有使用临时文件,因为我不想使用随机文件名(在某些设备上它会导致“文件名太长”错误)。它在除Android11之外的所有设备上都能完美运行。(我什至不需要在应用设置中... 查看详情