Làm thế nào để gửi yêu cầu POST?


260

Tôi tìm thấy kịch bản này trực tuyến:

import httplib, urllib
params = urllib.urlencode({'number': 12524, 'type': 'issue', 'action': 'show'})
headers = {"Content-type": "application/x-www-form-urlencoded",
            "Accept": "text/plain"}
conn = httplib.HTTPConnection("bugs.python.org")
conn.request("POST", "", params, headers)
response = conn.getresponse()
print response.status, response.reason
302 Found
data = response.read()
data
'Redirecting to <a href="http://bugs.python.org/issue12524">http://bugs.python.org/issue12524</a>'
conn.close()

Nhưng tôi không hiểu cách sử dụng nó với PHP hoặc mọi thứ bên trong biến params là gì hoặc cách sử dụng nó. Tôi có thể vui lòng giúp đỡ một chút với việc cố gắng để làm việc này không?


1
Yêu cầu bài viết chỉ là yêu cầu bài viết, bất kể những gì ở phía máy chủ.
Ondra ižka

7
Điều này sẽ gửi một yêu cầu POST. Sau đó, máy chủ phản hồi với các tiêu đề 302 (chuyển hướng) đến POST của bạn. Điều gì thực sự sai?
ddinchev

1
Kịch bản này không giống với python3.2 compat
jdi

python3 tương đương với ví dụ này có thể là: pastebin.com/Rx4yfknM
jdi

1
Những gì tôi sẽ đề xuất là cài đặt live http headeraddon của firefox và hơn là mở url của bạn trong firefox và xem request/responseurl trong live http headeraddon hơn bạn sẽ hiểu những gì params and headerslàm trong mã của bạn.
RanRag

Câu trả lời:


388

Nếu bạn thực sự muốn xử lý bằng HTTP bằng Python, tôi khuyên bạn nên Yêu cầu: HTTP cho Con người . Khởi động nhanh POST phù hợp với câu hỏi của bạn là:

>>> import requests
>>> r = requests.post("http://bugs.python.org", data={'number': 12524, 'type': 'issue', 'action': 'show'})
>>> print(r.status_code, r.reason)
200 OK
>>> print(r.text[:300] + '...')

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<title>
Issue 12524: change httplib docs POST example - Python tracker

</title>
<link rel="shortcut i...
>>> 

Tôi không thể có được kết quả như bạn đã làm ở trên. Tôi đã viết một số vấn đề khác trên trang và sau đó chạy tập lệnh nhưng tôi không thể thấy số Vấn đề trên kết quả.
Efe Büyük

2
Vui lòng thay đổi dữ liệu = {'số': 12524, để đọc dữ liệu = {'số': '12524' ,. Tôi đã tự thay đổi nhưng chỉnh sửa cần nhiều hơn 6 ký tự. Cảm ơn
kevthanewversi

2
Làm thế nào để có được kết quả json?
Yohanes AI

9
Nếu bạn cần gửi một đối tượng JSON, bạn nên làm: json={'number': 12524...thay vìdata=...
Seraf

3
tại sao câu trả lời lại nói "Nếu bạn thực sự muốn xử lý bằng HTTP bằng Python"? nó có phải là một ý tưởng tồi để xử lý các yêu cầu HTTP không? nếu vậy thì tại sao? bất cứ ai có thể giải thích?
Jan Pisl

147

Nếu bạn cần tập lệnh của mình có thể di động và bạn không muốn có bất kỳ sự phụ thuộc nào của bên thứ 3, đây là cách bạn gửi yêu cầu POST hoàn toàn trong Python 3.

from urllib.parse import urlencode
from urllib.request import Request, urlopen

url = 'https://httpbin.org/post' # Set destination URL here
post_fields = {'foo': 'bar'}     # Set POST fields here

request = Request(url, urlencode(post_fields).encode())
json = urlopen(request).read().decode()
print(json)

Đầu ra mẫu:

{
  "args": {}, 
  "data": "", 
  "files": {}, 
  "form": {
    "foo": "bar"
  }, 
  "headers": {
    "Accept-Encoding": "identity", 
    "Content-Length": "7", 
    "Content-Type": "application/x-www-form-urlencoded", 
    "Host": "httpbin.org", 
    "User-Agent": "Python-urllib/3.3"
  }, 
  "json": null, 
  "origin": "127.0.0.1", 
  "url": "https://httpbin.org/post"
}

6
Mã này sẽ chỉ hoạt động trong Python 3, như tôi đã nói trong câu trả lời.
stil

36

Bạn không thể đạt được các yêu cầu POST bằng cách sử dụng urllib(chỉ dành cho GET), thay vào đó hãy thử sử dụng requestsmô-đun, ví dụ:

Ví dụ 1.0:

import requests

base_url="www.server.com"
final_url="/{0}/friendly/{1}/url".format(base_url,any_value_here)

payload = {'number': 2, 'value': 1}
response = requests.post(final_url, data=payload)

print(response.text) #TEXT/HTML
print(response.status_code, response.reason) #HTTP

Ví dụ 1.2:

>>> import requests

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

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

Ví dụ 1.3:

>>> import json

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

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

4
Cảm ơn. data = json.dumps (tải trọng) là chìa khóa cho usecase của tôi
Aram

11

Sử dụng requeststhư viện để NHẬN, POST, PUT hoặc XÓA bằng cách nhấn điểm cuối API REST. urlTruyền url điểm cuối api còn lại vào , tải trọng (dict) trong datavà tiêu đề / siêu dữ liệu trongheaders

import requests, json

url = "bugs.python.org"

payload = {"number": 12524, 
           "type": "issue", 
           "action": "show"}

header = {"Content-type": "application/x-www-form-urlencoded",
          "Accept": "text/plain"} 

response_decoded_json = requests.post(url, data=payload, headers=header)
response_json = response_decoded_json.json()

print response_json

2
Mã này có vấn đề với thụt lề và tên param tiêu đề.
xilopaint

2
headerstham số là sai và chúng tôi không có bất kỳ json ở đây. Chúng ta nên sử dụngjson.dumps(pauload)
Arash Hatami

Cảm ơn @xilopaint và ArashHatami về lỗi cú pháp. Sửa chữa ngay.
Pranzell

3

Từ điển dữ liệu của bạn bao gồm tên của các trường nhập mẫu, bạn chỉ cần giữ đúng giá trị của chúng để tìm kết quả. dạng xem tiêu đề cấu hình trình duyệt để lấy loại dữ liệu bạn khai báo. Với thư viện yêu cầu, thật dễ dàng để gửi POST:

import requests

url = "https://bugs.python.org"
data = {'@number': 12524, '@type': 'issue', '@action': 'show'}
headers = {"Content-type": "application/x-www-form-urlencoded", "Accept":"text/plain"}
response = requests.post(url, data=data, headers=headers)

print(response.text)

Tìm hiểu thêm về đối tượng Yêu cầu: https://requests.readthedocs.io/en/master/api/


1

Nếu bạn không muốn sử dụng một mô-đun bạn phải cài đặt như thế nào requestsvà trường hợp sử dụng của bạn là rất cơ bản, thì bạn có thể sử dụngurllib2

urllib2.urlopen(url, body)

Xem tài liệu urllib2tại đây: https://docs.python.org/2/l Library / urllib2.html .

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.