Загрузка PDF-файла с URL-адреса, который перенаправляет 2 раза, завершается неудачно даже при использовании request.history - PullRequest
0 голосов
/ 06 мая 2018

Я боролся с этим целый день. Я составляю список URL-адресов, которые я получаю, используя urllib3 на веб-странице (также используя BeautifulSoup). URL в основном указывают на PDF-файлы, которые я хотел автоматизировать загрузку. Что замечательно, так это то, что ссылки в формате PDF имеют красивый рисунок. Поэтому я легко использую регулярное выражение, чтобы составить список PDF-файлов, которые я хочу скачать, и игнорирую остальные. Но тут-то и начинается проблема. URL следуют шаблону http://www.ti.com/lit/sboa263

ПРИМЕЧАНИЕ. Последняя часть изменяется для других файлов и без расширения pdf.

Но если вы поместите эту ссылку в браузере, вы сможете ясно увидеть, как она меняется с * на 1007 *http://www.ti.com/general/docs/lit/getliterature.tsp?baseLiteratureNumber=sboa263, и в конечном итоге она меняется на http://www.ti.com/lit/an/sboa263/sboa263.pdf
Теперь я понимаю, что вы можете сказать мне: «Отлично, тогда следуйте этой схеме». Но я не хочу, потому что IMO это не правильный способ решить эту автоматизацию. Я хочу иметь возможность скачать PDF с первой ссылки.

Я попытался

<code>response = requests.get(url,allow_redirects=True)
, что приводит меня только к результату первого перенаправления, а НЕ к последнему файлу. Даже response.history ведет меня только к первому перенаправлению.

И когда я все равно пытаюсь скачать файл, я получаю поврежденный PDF, который не открывается. Однако, когда я вручную передаю окончательный URL-адрес только для проверки правильности записи в мой файл, я получаю фактический pdf в идеальном порядке. Я не понимаю, почему запросов не может получить окончательный URL. Мой полный код ниже для вашей справки -

from bs4 import BeautifulSoup
import urllib3
import re
http = urllib3.PoolManager()
url = 'http://www.ti.com/analog-circuit/circuit-cookbook.html'
response = http.request('GET', url)
soup = BeautifulSoup(response.data)
find = re.compile("http://www.ti.com/lit/")
download_links = []
for link in soup.find_all('a'):
    match = re.match(find, link.get('href'))
    if match:
        #print(link.get('href'))
        download_links.append(link.get('href'))

Чтобы попасть на перенаправленный URL, я использую -

import requests
response = requests.get(download_links[45])
if response.history:
    print ("Request was redirected")
    for resp in response.history:
        final_url = resp.url
response = requests.get(final_url)

Для загрузки файла я использовал код ниже -

with open('C:/Users/Dell/Desktop/test.pdf', 'wb') as f:
    f.write(response.content)

Кроме того, я бы просто хотел передать имя папки, и все файлы должны быть загружены с именем последней части самого URL. Мне еще предстоит выяснить, как это сделать. Я пытался шутилс , но это не сработало. Если бы вы могли помочь мне с этой частью тоже было бы здорово.

РЕДАКТИРОВАТЬ: Я передал первые два URL-адреса Почтальону, и я получил HTML, а при передаче третьего URL-адреса загружается PDF. В HTML, который я получаю, я ясно вижу, что одно из свойств Meta перечисляет окончательный PDF-URL. Вот часть результата Почтальона, которая имеет отношение к делу -

<!DOCTYPE html>
<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
        <meta content="IE=8;IE=9;IE=edge" http-equiv="x-ua-compatible">
        <meta content='width=device-width, initial-scale=1.0' name='viewport'>
        <META HTTP-EQUIV="Pragma" CONTENT="no-cache">
        <META HTTP-EQUIV="Expires" CONTENT="-1">
        <META HTTP-EQUIV="Refresh" CONTENT="1; URL=http://www.ti.com/lit/an/sboa263/sboa263.pdf">

Части ниже также показывают окончательный URL, но я думаю, вы поняли идею. Можем ли мы использовать эту информацию?

1 Ответ

0 голосов
/ 12 мая 2018

Как упомянуто Miraj50 , это действительно был Meta Refresh, который привел его к последнему URL. Итак, я извлек последние URL-адреса из мета-тега и смог загрузить все 45 PDF-файлов. Ниже код для того же -

for links in download_links[5:]:
    response = requests.get(links)
    if response.history:
        print ("Request was redirected")
        print(response.url)
        r = response.url

Получение ссылок из метатега -

# The redirected url then uses meta refresh
meta_response = http.request('GET', r)
meta_soup = BeautifulSoup(meta_response.data)
meta_result = meta_soup.find('meta',attrs={'http-equiv':'Refresh'})
#print(meta_result)
wait,text = meta_result["content"].split(";")
final_url = text.strip()[4:]
...