Vous devez utiliser le files
paramètre pour envoyer une demande POST de formulaire en plusieurs parties même lorsque vous n'avez pas besoin de télécharger de fichiers.
De la source des demandes d' origine:
def request(method, url, **kwargs):
"""Constructs and sends a :class:`Request <Request>`.
...
:param files: (optional) Dictionary of ``'name': file-like-objects``
(or ``{'name': file-tuple}``) for multipart encoding upload.
``file-tuple`` can be a 2-tuple ``('filename', fileobj)``,
3-tuple ``('filename', fileobj, 'content_type')``
or a 4-tuple ``('filename', fileobj, 'content_type', custom_headers)``,
where ``'content-type'`` is a string
defining the content type of the given file
and ``custom_headers`` a dict-like object
containing additional headers to add for the file.
La partie pertinente est: file-tuple can be a
2-tuple
, .3-tuple
or a
4-tuple
Sur la base de ce qui précède, la demande de formulaire en plusieurs parties la plus simple qui comprend à la fois les fichiers à télécharger et les champs de formulaire ressemblera à ceci:
multipart_form_data = {
'file2': ('custom_file_name.zip', open('myfile.zip', 'rb')),
'action': (None, 'store'),
'path': (None, '/path1')
}
response = requests.post('https://httpbin.org/post', files=multipart_form_data)
print(response.content)
☝ Notez le None
comme premier argument dans le tuple pour les champs de texte brut - il s'agit d'un espace réservé pour le champ de nom de fichier qui n'est utilisé que pour les téléchargements de fichiers, mais pour les champs de texte passant None
comme premier paramètre est requis pour que les données soient soumises .
Plusieurs champs avec le même nom
Si vous devez publier plusieurs champs avec le même nom, au lieu d'un dictionnaire, vous pouvez définir votre charge utile comme une liste (ou un tuple) de tuples:
multipart_form_data = (
('file2', ('custom_file_name.zip', open('myfile.zip', 'rb'))),
('action', (None, 'store')),
('path', (None, '/path1')),
('path', (None, '/path2')),
('path', (None, '/path3')),
)
API de requêtes de streaming
Si l'API ci-dessus n'est pas assez pythonique pour vous, alors envisagez d'utiliser la barre d' outils de requêtes ( pip install requests_toolbelt
) qui est une extension du module de requêtes principal qui prend en charge le streaming de téléchargement de fichiers ainsi que le MultipartEncoder qui peut être utilisé à la place defiles
, et qui permet également vous définissez la charge utile comme un dictionnaire, un tuple ou une liste.
MultipartEncoder
peut être utilisé à la fois pour les demandes en plusieurs parties avec ou sans champs de téléchargement réels. Il doit être affecté au data
paramètre.
import requests
from requests_toolbelt.multipart.encoder import MultipartEncoder
multipart_data = MultipartEncoder(
fields={
# a file upload field
'file': ('file.zip', open('file.zip', 'rb'), 'text/plain')
# plain text fields
'field0': 'value0',
'field1': 'value1',
}
)
response = requests.post('http://httpbin.org/post', data=multipart_data,
headers={'Content-Type': multipart_data.content_type})
Si vous devez envoyer plusieurs champs avec le même nom, ou si l'ordre des champs du formulaire est important, alors un tuple ou une liste peut être utilisé à la place d'un dictionnaire:
multipart_data = MultipartEncoder(
fields=(
('action', 'ingest'),
('item', 'spam'),
('item', 'sausage'),
('item', 'eggs'),
)
)