Модуль http в python

Python requests post value

The method dispatches a POST request on the given
URL, providing the key/value pairs for the fill-in form content.

post_value.py

#!/usr/bin/env python3

import requests as req

data = {'name': 'Peter'}

resp = req.post("https://httpbin.org/post", data)
print(resp.text)

The script sends a request with a key having value.
The POST request is issued with the method.

$ ./post_value.py
{
  "args": {},
  "data": "",
  "files": {},
  "form": {
    "name": "Peter"
  },
  "headers": {
    "Accept": "*/*",
    "Accept-Encoding": "gzip, deflate",
    "Content-Length": "10",
    "Content-Type": "application/x-www-form-urlencoded",
    "Host": "httpbin.org",
    "User-Agent": "python-requests/2.21.0"
  },
  "json": null,
  ...
}

This is the output of the script.

Объект сеанса

Объект сеанса в основном используется для сохранения определенных параметров, например файлов cookie, в различных HTTP-запросах. Объект сеанса может использовать одно TCP-соединение для обработки нескольких сетевых запросов и ответов, что приводит к повышению производительности.

import requests

first_session = requests.Session()
second_session = requests.Session()

first_session.get('http://httpbin.org/cookies/set/cookieone/111')
r = first_session.get('http://httpbin.org/cookies')
print(r.text)

second_session.get('http://httpbin.org/cookies/set/cookietwo/222')
r = second_session.get('http://httpbin.org/cookies')
print(r.text)

r = first_session.get('http://httpbin.org/anything')
print(r.text)

Вывод:

{"cookies":{"cookieone":"111"}}

{"cookies":{"cookietwo":"222"}}

{"args":{},"data":"","files":{},"form":{},"headers":{"Accept":"*/*","Accept-Encoding":"gzip, deflate","Connection":"close","Cookie":"cookieone=111","Host":"httpbin.org","User-Agent":"python-requests/2.9.1"},"json":null,"method":"GET","origin":"103.9.74.222","url":"http://httpbin.org/anything"}

Путь httpbin/cookies/set /{имя}/{значение} установит файл cookie с именем и значением. Здесь мы устанавливаем разные значения cookie для объектов first_session и second_session. Вы можете видеть, что один и тот же файл cookie возвращается во всех будущих сетевых запросах для определенного сеанса.

Точно так же мы можем использовать объект сеанса для сохранения определенных параметров для всех запросов.

import requests

first_session = requests.Session()

first_session.cookies.update({'default_cookie': 'default'})

r = first_session.get('http://httpbin.org/cookies', cookies={'first-cookie': '111'})
print(r.text)

r = first_session.get('http://httpbin.org/cookies')
print(r.text)

Вывод:

{"cookies":{"default_cookie":"default","first-cookie":"111"}}

{"cookies":{"default_cookie":"default"}}

Как видите, default_cookie отправляется с каждым запросом сеанса. Если мы добавим какой-либо дополнительный параметр к объекту cookie, он добавится к файлу default_cookie. «first-cookie»: «111» добавляется к cookie по умолчанию «default_cookie»:»default».

Main Interface¶

All of Requests’ functionality can be accessed by these 7 methods.
They all return an instance of the object.

requests.request(method, url, **kwargs)

Constructs and sends a .

Parameters
  • method – method for the new object: , , , , , , or .

  • url – URL for the new object.

  • params – (optional) Dictionary, list of tuples or bytes to send
    in the query string for the .

  • data – (optional) Dictionary, list of tuples, bytes, or file-like
    object to send in the body of the .

  • json – (optional) A JSON serializable Python object to send in the body of the .

  • headers – (optional) Dictionary of HTTP Headers to send with the .

  • cookies – (optional) Dict or CookieJar object to send with the .

  • files – (optional) Dictionary of (or ) for multipart encoding upload.
    can be a 2-tuple , 3-tuple
    or a 4-tuple , where is a string
    defining the content type of the given file and a dict-like object containing additional headers
    to add for the file.

  • auth – (optional) Auth tuple to enable Basic/Digest/Custom HTTP Auth.

  • timeout ( or ) – (optional) How many seconds to wait for the server to send data
    before giving up, as a float, or a tuple.

  • allow_redirects () – (optional) Boolean. Enable/disable GET/OPTIONS/POST/PUT/PATCH/DELETE/HEAD redirection. Defaults to .

  • proxies – (optional) Dictionary mapping protocol to the URL of the proxy.

  • verify – (optional) Either a boolean, in which case it controls whether we verify
    the server’s TLS certificate, or a string, in which case it must be a path
    to a CA bundle to use. Defaults to .

  • stream – (optional) if , the response content will be immediately downloaded.

  • cert – (optional) if String, path to ssl client cert file (.pem). If Tuple, (‘cert’, ‘key’) pair.

Returns

object

Return type

Usage:

>>> import requests
>>> req = requests.request('GET', 'https://httpbin.org/get')
>>> req
<Response >
requests.head(url, **kwargs)

Sends a HEAD request.

Parameters
  • url – URL for the new object.

  • **kwargs – Optional arguments that takes. If
    allow_redirects is not provided, it will be set to False (as
    opposed to the default behavior).

Returns

object

Return type
requests.get(url, params=None, **kwargs)

Sends a GET request.

Parameters
  • url – URL for the new object.

  • params – (optional) Dictionary, list of tuples or bytes to send
    in the query string for the .

  • **kwargs – Optional arguments that takes.

Returns

object

Return type
requests.post(url, data=None, json=None, **kwargs)

Sends a POST request.

Parameters
  • url – URL for the new object.

  • data – (optional) Dictionary, list of tuples, bytes, or file-like
    object to send in the body of the .

  • json – (optional) json data to send in the body of the .

  • **kwargs – Optional arguments that takes.

Returns

object

Return type
requests.put(url, data=None, **kwargs)

Sends a PUT request.

Parameters
  • url – URL for the new object.

  • data – (optional) Dictionary, list of tuples, bytes, or file-like
    object to send in the body of the .

  • json – (optional) json data to send in the body of the .

  • **kwargs – Optional arguments that takes.

Returns

object

Return type
requests.patch(url, data=None, **kwargs)

Sends a PATCH request.

Parameters
  • url – URL for the new object.

  • data – (optional) Dictionary, list of tuples, bytes, or file-like
    object to send in the body of the .

  • json – (optional) json data to send in the body of the .

  • **kwargs – Optional arguments that takes.

Returns

object

Return type

POST

Чтобы отправить и проверить POST запрос внесите небольшие изменения в код.

Очевидно, что GET нужно заменить на POST, также params нужно заменить на data

url: https://httpbin.org/post
text:
{
«args»: {},
«data»: «»,
«files»: {},
«form»: {
«established»: «2018»,
«website»: «heihei.ru»
},
«headers»: {
«Accept»: «*/*»,
«Accept-Encoding»: «gzip, deflate»,
«Content-Length»: «34»,
«Content-Type»: «application/x-www-form-urlencoded»,
«Host»: «httpbin.org»,
«User-Agent»: «python-requests/2.24.0»,
«X-Amzn-Trace-Id»: «Root=1-5f8c30ac-6b32899f073f9df4055c55c4»
},
«json»: null,
«origin»: «87.92.8.47»,
«url»: «https://httpbin.org/post»
}

Ответы, которые мы получили с httpbin приходили в формате json

Для работы c json бывает удобно
использовать встроенный метод .json()

В этом случае данные записываются в словарь и к ним очень легко обращаться.

Обратите внимание на «form» данные, которые были переданы возвращаются в этом поле.

Изменим код так, чтобы на экран выводились только эти данные. python3 rdemo.py

python3 rdemo.py

{‘established’: ‘2018’, ‘website’: ‘heihei.ru’}

Работа с JSON ответами

import requests

r = requests.get("https://egorovegor.ru/wp-json/")

print (r.json())

Ответ сервера:

Обратите внимание, я сократил ответ сервера из за большого количества информации в json. r.json() разбирает ответ в Python-совместимый тип данных, т.е

словарь или список. Разберем на примере как использовать полученные JSON данные

r.json() разбирает ответ в Python-совместимый тип данных, т.е. словарь или список. Разберем на примере как использовать полученные JSON данные.

import requests

r = requests.get("https://egorovegor.ru/wp-json/")

data = r.json()
name = data
description = data
url = data
timezone = data

print(f"Информация о сайте: {url}")
print(f"Название: {name}")
print(f"Описание: {description}")
print(f"Часовой пояс: {timezone}")

Выполнив данный сценарий мы получим результат указанный ниже.

Информация о сайте: https://egorovegor.ru
Название: Cайт Егорова Егора
Описание: Технологии, интернет-маркетинг и Python
Часовой пояс: Europe/Moscow

Получение SSL: ошибка CERTIFICATE_VERIFY_FAILED

Когда я впервые выполнил указанную выше программу, я получил следующую ошибку, связанную с сертификатами SSL.

$ python3.6 http_client.py 
Traceback (most recent call last):
  File "http_client.py", line 4, in <module>
    connection.request("GET", "/")
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/http/client.py", line 1239, in request
    self._send_request(method, url, body, headers, encode_chunked)
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/http/client.py", line 1285, in _send_request
    self.endheaders(body, encode_chunked=encode_chunked)
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/http/client.py", line 1234, in endheaders
    self._send_output(message_body, encode_chunked=encode_chunked)
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/http/client.py", line 1026, in _send_output
    self.send(msg)
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/http/client.py", line 964, in send
    self.connect()
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/http/client.py", line 1400, in connect
    server_hostname=server_hostname)
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/ssl.py", line 401, in wrap_socket
    context=self, session=session)
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/ssl.py", line 808, in init
    self.do_handshake()
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/ssl.py", line 1061, in do_handshake
    self._sslobj.do_handshake()
  File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/ssl.py", line 683, in do_handshake
    self._sslobj.do_handshake()
ssl.SSLError:  certificate verify failed (_ssl.c:748)
$ 

Из вывода было ясно, что он должен что-то делать с сертификатами SSL. Но сертификат веб-сайта в порядке, так что это должно быть что-то с настройкой. После некоторого поиска в Google я обнаружил, что в MacOS нам нужно запустить файл Install Certificates.command, находящийся в каталоге установки в Python, чтобы исправить эту проблему. На изображении ниже показан результат выполнения этой команды, похоже, что он устанавливает последние сертификаты, которые будут использоваться при создании SSL-соединений.

Обратите внимание, что я получил эту ошибку в Mac OS. Однако в моей системе Ubuntu он работал отлично

Чтение ответа

Ответ на HTTP-запрос может содержать множество заголовков, содержащих различную информацию.

httpbin – популярный веб-сайт для тестирования различных операций HTTP. В этой статье мы будем использовать httpbin или get для анализа ответа на запрос GET. Прежде всего, нам нужно узнать заголовок ответа и то, как он выглядит. Вы можете использовать любой современный веб-браузер, чтобы найти его, но для этого примера мы будем использовать браузер Google Chrome:

  • В Chrome откройте URL-адрес http://httpbin.org/get, щелкните правой кнопкой мыши в любом месте страницы и выберите параметр «Проверить».
  • Это откроет новое окно в вашем браузере. Обновите страницу и перейдите на вкладку «Сеть».
  • Эта вкладка «Сеть» покажет вам все различные типы сетевых запросов, сделанных браузером. Щелкните запрос «получить» в столбце «Имя» и выберите вкладку «Заголовки» справа.

Содержание «Заголовков ответа» является нашим обязательным элементом. Вы можете увидеть пары ключ-значение, содержащие различную информацию о ресурсе и запросе. Попробуем разобрать эти значения с помощью библиотеки запросов:

import requests

r = requests.get('http://httpbin.org/get')
print(r.headers)
print(r.headers)
print(r.headers)
print(r.headers)
print(r.headers)
print(r.headers)
print(r.headers)
print(r.headers)

Мы получили информацию заголовка с помощью r.headers, и мы можем получить доступ к каждому значению заголовка с помощью определенных ключей

Обратите внимание, что ключ не чувствителен к регистру.. Точно так же попробуем получить доступ к значению ответа

Заголовок выше показывает, что ответ находится в формате JSON: (Content-type: application/json). Библиотека запросов поставляется с одним встроенным парсером JSON, и мы можем использовать request.get (‘url’). Json() для анализа его как объекта JSON. Затем значение для каждого ключа результатов ответа можно легко проанализировать, как показано ниже:

Точно так же попробуем получить доступ к значению ответа. Заголовок выше показывает, что ответ находится в формате JSON: (Content-type: application/json). Библиотека запросов поставляется с одним встроенным парсером JSON, и мы можем использовать request.get (‘url’). Json() для анализа его как объекта JSON. Затем значение для каждого ключа результатов ответа можно легко проанализировать, как показано ниже:

import requests

r = requests.get('http://httpbin.org/get')

response = r.json()
print(r.json())
print(response)
print(response)
print(response)
print(response)
print(response)
print(response)
print(response)
print(response)
print(response)

Приведенный выше код напечатает следующий вывод:

{'headers': {'Host': 'httpbin.org', 'Accept-Encoding': 'gzip, deflate', 'Connection': 'close', 'Accept': '*/*', 'User-Agent': 'python-requests/2.9.1'}, 'url': 'http://httpbin.org/get', 'args': {}, 'origin': '103.9.74.222'}
{}
{'Host': 'httpbin.org', 'Accept-Encoding': 'gzip, deflate', 'Connection': 'close', 'Accept': '*/*', 'User-Agent': 'python-requests/2.9.1'}
*/*
gzip, deflate
close
httpbin.org
python-requests/2.9.1
103.9.74.222
http://httpbin.org/get

Третья строка, ierjson(), напечатала значение ответа JSON. Мы сохранили значение JSON в ответе переменной, а затем распечатали значение для каждого ключа

Обратите внимание, что в отличие от предыдущего примера, пара «ключ-значение» чувствительна к регистру.

Подобно JSON и текстовому контенту, мы можем использовать запросы для чтения контента ответа в байтах для нетекстовых запросов, используя свойство .content. Это автоматически декодирует gzip и дефлирует закодированные файлы.

Redirection and History¶

By default Requests will perform location redirection for all verbs except
HEAD.

We can use the property of the Response object to track redirection.

The list contains the
objects that were created in order to
complete the request. The list is sorted from the oldest to the most recent
response.

For example, GitHub redirects all HTTP requests to HTTPS:

>>> r = requests.get('http://github.com/')

>>> r.url
'https://github.com/'

>>> r.status_code
200

>>> r.history
>]

If you’re using GET, OPTIONS, POST, PUT, PATCH or DELETE, you can disable
redirection handling with the parameter:

>>> r = requests.get('http://github.com/', allow_redirects=False)

>>> r.status_code
301

>>> r.history
[]

If you’re using HEAD, you can enable redirection as well:

Автодокументирование кода

Для того чтобы облегчить написание документации и улучшить ее в целом, существуют различные Python-пакеты. Один из них — pyment.

Pyment работает следующим образом:

  1. Анализирует один или несколько скриптов.
  2. Получает существующие строки документации.
  3. Генерирует отформатированные строки документации со всеми параметрами, значениями по умолчанию и т.д.
  4. Далее вы можете применить сгенерированные строки к своим файлам.

Этот инструмент особенно полезен когда код плохо задокументирован, или когда документация вовсе отсутствует. Также pyment будет полезен в команде разработчиков для форматирования документации в едином стиле.

Установка:

Использование:

Для большинства IDE также существуют плагины, помогающие документировать код:

  • AutoDocstring – для VS Code.
  • Auto​Docstring – для SublimeText.
  • Python DocBlock Package – для Atom.
  • Autodoc – для PyCharm.

В PyCharm существует встроенный функционал добавления документации к коду. Для этого нужно:

  1. Переместить курсор под объявление функции.
  2. Написать тройные кавычки «»» и нажмите «Enter».

6: Использование Translate API

Теперь давайте попробуем использовать Yandex Translate API для выполнения запроса на перевод текста на другой язык.

Чтобы использовать API, сначала необходимо зарегистрироваться. После регистрации перейдите в Translate API и создайте ключ API. Получив ключ, добавьте его в свой файл script.py как константу.

Вот ссылка, по которой можно все сделать.

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

Узнать, какой URL нужно отправить, чтобы использовать API, можно в документации Яндекса.

Там можно найти всю информацию, необходимую для использования Translate API для перевода текста.

Если в URL вы видите амперсанды (&), вопросительные знаки (?) и знаки равенства (=), вы можете быть уверены, что такой URL предназначен для запросов GET. Эти символы задают соответствующие параметры URL-адреса.

Обычно в квадратных скобках ([]) указываются опциональные фрагменты. В этом случае таковыми являются format, options и callback, в то время как key, text, and lang обязательно должны присутствовать в запросе.

Давайте добавим код для отправки запроса на этот URL. Вы можете заменить первый созданный нами запрос в файле script.py следующим кодом:

Есть два способа добавить параметры. Их можно добавить в конец URL-адреса напрямую, а можно сделать так, чтобы запросы делали это за нас. Чтобы сделать последнее, мы можем создать словарь для наших параметров. Обязательными элементами будут ключ, текст и язык. Давайте создадим словарь, используя ключ API, текст ‘Hello’ и языки ‘en-es’ (то есть текст нужно перевести с английского на испанский).

Другие языковые коды вы можете найти здесь в столбце 639-1.

Давайте создадим словарь параметров, используя функцию dict(), и передадим ей ключи и значения, которые должны быть в этом словаре. Добавьте в файл script.py:

Теперь мы возьмем словарь параметров и передадим его в функцию .get().

После этого запросы начнут добавляться к URL-адресу самостоятельно.

Теперь давайте добавим оператор print для текста ответа и посмотрим, что вернется в результате.

Здесь мы видим три вещи. Сначала идет код состояния, который в точности совпадает с кодом состояния самого ответа; затем идет язык, который мы выбрали; в конце мы видим переведенный текст.

Попробуйте еще раз, указав в качестве языка en-fr, и вы должны увидеть «Bonjour» в ответе.

Давайте посмотрим на заголовки для этого конкретного ответа.

Очевидно, заголовки будут отличаться, потому что мы обращаемся к другому серверу. В этом случае тип контента – application/json, а не text/html. Это означает, что данные могут быть интерпретированы как JSON.

Когда application/json является типом контента, мы можем сделать так, чтобы запросы преобразовывали ответ в словарь и список, чтобы легче получать доступ к данным.

Чтобы данные были обработаны как JSON, мы используем метод .json() для объекта ответа.

Если вы отобразите его, вы увидите, что данные выглядят так же, но формат немного отличается.

Теперь это не простой текст, который вы получаете из res.text, а версия словаря.

Допустим, мы хотим получить доступ к тексту. Поскольку теперь это словарь, мы можем использовать ключ text.

И теперь мы увидим только данные для этого ключа. В этом случае мы получим список из одного элемента. Если вам нужно получить этот текст в списке, можно получить к нему доступ по индексу.

И теперь на экране будет только переведенное слово.

Меняя параметры, вы будете получать разные результаты. Давайте изменим текст, вместо Hello будет Goodbye, а также изменим целевой язык на испанский и отправим запрос снова.

Также можно попробовать перевести более длинный текст на другие языки и посмотреть, какие ответы дает API.

Python requests credentials

The parameter provides a basic HTTP authentication; it takes
a tuple of a name and a password to be used for a realm. A security realm
is a mechanism used for protecting web application resources.

$ sudo apt-get install apache2-utils
$ sudo htpasswd -c /etc/nginx/.htpasswd user7
New password:
Re-type new password:
Adding password for user user7

We use the tool to create a user name and a password
for basic HTTP authentication.

location /secure {

        auth_basic "Restricted Area";
        auth_basic_user_file /etc/nginx/.htpasswd;
}

Inside the nginx configuration file,
we create a secured page. The name of the realm is «Restricted Area».

index.html

<!DOCTYPE html>
<html lang="en">
<head>
<title>Secure page</title>
</head>

<body>

<p>
This is a secure page.
</p>

</body>

</html>

Inside the directory, we have
this HTML file.

credentials.py

#!/usr/bin/env python3

import requests as req

user = 'user7'
passwd = '7user'

resp = req.get("http://localhost/secure/", auth=(user, passwd))
print(resp.text)

The script connects to the secure webpage; it provides the user name
and the password necessary to access the page.

$ ./credentials.py
<!DOCTYPE html>
<html lang="en">
<head>
<title>Secure page</title>
</head>

<body>

<p>
This is a secure page.
</p>

</body>

</html>

With the right credentials, the script returns
the secured page.

In this tutorial, we have worked with the Python Requests module.

List .

POST Multiple Multipart-Encoded Files¶

You can send multiple files in one request. For example, suppose you want to
upload image files to an HTML form with a multiple file field ‘images’:

<input type="file" name="images" multiple="true" required="true"/>

To do that, just set files to a list of tuples of :

>>> url = 'https://httpbin.org/post'
>>> multiple_files = 
...     ('images', ('foo.png', open('foo.png', 'rb'), 'image/png')),
...     ('images', ('bar.png', open('bar.png', 'rb'), 'image/png'))]
>>> r = requests.post(url, files=multiple_files)
>>> r.text
{
  ...
  'files': {'images': 'data:image/png;base64,iVBORw ....'}
  'Content-Type': 'multipart/form-data; boundary=3131623adb2043caaeb5538cc7aa0b3a',
  ...
}

More complicated POST requests¶

Typically, you want to send some form-encoded data — much like an HTML form.
To do this, simply pass a dictionary to the argument. Your
dictionary of data will automatically be form-encoded when the request is made:

>>> payload = {'key1' 'value1', 'key2' 'value2'}

>>> r = requests.post("https://httpbin.org/post", data=payload)
>>> print(r.text)
{
  ...
  "form": {
    "key2": "value2",
    "key1": "value1"
  },
  ...
}

The argument can also have multiple values for each key. This can be
done by making either a list of tuples or a dictionary with lists
as values. This is particularly useful when the form has multiple elements that
use the same key:

>>> payload_tuples = 
>>> r1 = requests.post('https://httpbin.org/post', data=payload_tuples)
>>> payload_dict = {'key1' 'value1', 'value2']}
>>> r2 = requests.post('https://httpbin.org/post', data=payload_dict)
>>> print(r1.text)
{
  ...
  "form": {
    "key1": [
      "value1",
      "value2"

  },
  ...
}
>>> r1.text == r2.text
True

There are times that you may want to send data that is not form-encoded. If
you pass in a instead of a , that data will be posted directly.

For example, the GitHub API v3 accepts JSON-Encoded POST/PATCH data:

>>> import json

>>> url = 'https://api.github.com/some/endpoint'
>>> payload = {'some' 'data'}

>>> r = requests.post(url, data=json.dumps(payload))

Instead of encoding the yourself, you can also pass it directly using
the parameter (added in version 2.4.2) and it will be encoded automatically:

>>> url = 'https://api.github.com/some/endpoint'
>>> payload = {'some' 'data'}

>>> r = requests.post(url, json=payload)

Note, the parameter is ignored if either or is passed.

Response Content¶

We can read the content of the server’s response. Consider the GitHub timeline
again:

>>> import requests

>>> r = requests.get('https://api.github.com/events')
>>> r.text
'[{"repository":{"open_issues":0,"url":"https://github.com/...

Requests will automatically decode content from the server. Most unicode
charsets are seamlessly decoded.

When you make a request, Requests makes educated guesses about the encoding of
the response based on the HTTP headers. The text encoding guessed by Requests
is used when you access . You can find out what encoding Requests is
using, and change it, using the property:

>>> r.encoding
'utf-8'
>>> r.encoding = 'ISO-8859-1'

If you change the encoding, Requests will use the new value of
whenever you call . You might want to do this in any situation where
you can apply special logic to work out what the encoding of the content will
be. For example, HTML and XML have the ability to specify their encoding in
their body. In situations like this, you should use to find the
encoding, and then set . This will let you use with
the correct encoding.

Using Python request headers

Python request headers hold important data related to the message

Response headers are another important part of the request. While they do not contain any content of the original message, headers hold many important details of the response such as information about the server, the date, encoding, etc. Every detail can be acquired from the initial response by making a call:

As with the .json() call, headers create a dictionary type object which can then be accessed. Adding parameters to the call will list out a part of the response, e.g.:

Our function will now print the date stored in the response header. Values are considered case-insensitive, therefore Requests will output the same result regardless of whether the parameter was formed as ‘date’ or ‘Date’.

You can also send custom Python requests headers. Dictionary-type objects are used yet again, although this time they have to be created. Headers are passed in an identical manner to parameters. To check whether our request header has been sent successfully we will need to make the call response.request.headers:

Running our code should output the request header in the debugger window with the user agent stated as ‘my-agent/1.0.1’. As a general rule, sending most common user agents is recommended as otherwise some websites could return a 403 ‘Forbidden’ response.

Custom HTTP headers are usually used for troubleshooting or informational purposes. User agents are often utilized in web scraping projects in order to change the perceived source of incoming requests.

Python requests: POST

Sending a Python POST request is the second most used HTTP method. They are used to create a resource on a server with specified data.  Sending a POST request is almost as simple as sending a GET:

Of course, all HTTP methods (HEAD is an exception) return a response body which can be read. Responses to POST requests can be read in the same manner as GET (or any other method):

Responses, rather obviously, in the relation to the types of requests made. For example, a POST request response contains information regarding the data sent to the server.

In most cases, specifying the data in the POST request might not be enough. Requests library accepts arguments from dictionary objects which can be utilized to send more advanced data:

Our new request would send the payload object to the destination server. At times, sending JSON POST requests can be necessary. Requests have an added feature that automatically converts the POST request data into JSON.

Alternatively, the json library might be used to convert dictionaries into JSON objects. A new import will be required to change the object type:

Note that the “json” argument is overridden if either “data” or “files” is used. Requests will only accept one of the three in a single POST.

Обработка таймаутов

Другая важная конфигурация сообщает нашей библиотеке, как обрабатывать тайм-ауты или запросы, на возврат которых уходит слишком много времени. Мы можем настроить запросы, чтобы они перестали ждать сетевых запросов, используя параметр тайм-аута.

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

import requests

requests.get('http://www.google.com', timeout=1)

Здесь будет выброшено исключение, если сервер не ответит в течение 1 секунды (что по-прежнему агрессивно для реального приложения). Чтобы это происходило чаще (для примера), вам нужно установить предел тайм-аута на гораздо меньшее значение, например 0,001.

Тайм-аут может быть настроен как для операций «подключения», так и для «чтения» запроса с использованием кортежа, что позволяет указать оба значения отдельно:

import requests

requests.get('http://www.google.com', timeout=(5, 14))

Здесь таймаут «подключения» составляет 5 секунд, а таймаут «чтения» – 14 секунд. Это позволит вашему запросу завершиться ошибкой намного быстрее, если он не может подключиться к ресурсу, а если он все же подключится, это даст ему больше времени для загрузки данных.

Authentication

Authentication helps a service understand who you are. Typically, you provide your credentials to a server by passing data through the header or a custom header defined by the service. All the request functions you’ve seen to this point provide a parameter called , which allows you to pass your credentials.

One example of an API that requires authentication is GitHub’s API. This endpoint provides information about the authenticated user’s profile. To make a request to the Authenticated User API, you can pass your GitHub username and password in a tuple to :

>>>

The request succeeded if the credentials you passed in the tuple to are valid. If you try to make this request with no credentials, you’ll see that the status code is :

>>>

When you pass your username and password in a tuple to the parameter, is applying the credentials using HTTP’s Basic access authentication scheme under the hood.

Therefore, you could make the same request by passing explicit Basic authentication credentials using :

>>>

Though you don’t need to be explicit for Basic authentication, you may want to authenticate using another method. provides other methods of authentication out of the box such as and .

You can even supply your own authentication mechanism. To do so, you must first create a subclass of . Then, you implement :

Here, your custom mechanism receives a token, then includes that token in the header of your request.

Bad authentication mechanisms can lead to security vulnerabilities, so unless a service requires a custom authentication mechanism for some reason, you’ll always want to use a tried-and-true auth scheme like Basic or OAuth.

While you’re thinking about security, let’s consider dealing with SSL Certificates using .

Получаем содержимое страницы в Requests

Нередко ответ на GET-запрос включает в себя довольно ценную информацию. Эта информация находится в теле сообщения и её называют payload. Применяя атрибуты и методы библиотеки Response, мы сможем получить payload в разных форматах.

Если хотим получить содержимое запроса в байтах, нужно использовать .content.

    >>> response = requests.get('https://api.github.com')
>>> response.content

Применение .content обеспечивает нам доступ к любым данным в теле запроса. Но нередко надо конвертировать полученные данные в строку с кодировкой UTF-8. Для этого выполняем команду response.text. По умолчанию requests пытается узнать текущую кодировку по заголовкам HTTP. Но мы можем указать нужную кодировку путём добавления перед .text .encoding.

>>> response.encoding = 'utf-8' # Optional: requests infers this internally
>>> response.text

Request and Response Objects¶

Whenever a call is made to and friends, you are doing two
major things. First, you are constructing a object which will be
sent off to a server to request or query some resource. Second, a
object is generated once Requests gets a response back from the server.
The object contains all of the information returned by the server and
also contains the object you created originally. Here is a simple
request to get some very important information from Wikipedia’s servers:

>>> r = requests.get('https://en.wikipedia.org/wiki/Monty_Python')

If we want to access the headers the server sent back to us, we do this:

>>> r.headers
{'content-length': '56170', 'x-content-type-options': 'nosniff', 'x-cache':
'HIT from cp1006.eqiad.wmnet, MISS from cp1010.eqiad.wmnet', 'content-encoding':
'gzip', 'age': '3080', 'content-language': 'en', 'vary': 'Accept-Encoding,Cookie',
'server': 'Apache', 'last-modified': 'Wed, 13 Jun 2012 01:33:50 GMT',
'connection': 'close', 'cache-control': 'private, s-maxage=0, max-age=0,
must-revalidate', 'date': 'Thu, 14 Jun 2012 12:59:39 GMT', 'content-type':
'text/html; charset=utf-8', 'x-cache-lookup': 'HIT from cp1006.eqiad.wmnet:3128,
MISS from cp1010.eqiad.wmnet:80'}

However, if we want to get the headers we sent the server, we simply access the
request, and then the request’s headers:

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

Adblock
detector