Я пытаюсь преобразовать этот фрагмент кода из PHP в Python (новичок в программировании), и мне трудно это сделать:
PHP, который я пытаюсь преобразовать, выглядит следующим образом:
$fp = fsockopen($whmcsurl, 80, $errno, $errstr, 5); if ($fp) { $querystring = ""; foreach ($postfields AS $k=>$v) { $querystring .= "$k=".urlencode($v)."&"; } $header="POST ".$whmcsurl."modules/servers/licensing/verify.php HTTP/1.0\r\n"; $header.="Host: ".$whmcsurl."\r\n"; $header.="Content-type: application/x-www-form-urlencoded\r\n"; $header.="Content-length: ".@strlen($querystring)."\r\n"; $header.="Connection: close\r\n\r\n"; $header.=$querystring; $data=""; @stream_set_timeout($fp, 20); @fputs($fp, $header); $status = @socket_get_status($fp); while (!@feof($fp)&&$status) { $data .= @fgets($fp, 1024); $status = @socket_get_status($fp); } @fclose ($fp); }
Соответствующий код Python, который я написал, выглядит следующим образом:
fp = socket.socket(socket.AF_INET,socket.SOCK_STREAM) fp.connect(("my ip", 80)) if (fp): querystring = "" #print postfields for key in postfields: querystring = querystring+key+"="+urllib.quote(str(postfields[key]))+"&" header = "POST "+whmcsurl+"modules/servers/licensing/verify.php HTTP/1.0\r\n" header+="Content-type: application/x-www-form-urlencoded\r\n" header+="Content-length: "+str(len(querystring))+"\r\n" header+="Connection: close\r\n\r\n" #header+=querystring data="" request = urllib2.Request(whmcsurl,querystring,header) response = urllib2.urlopen(request) data = response.read()
Здесь я столкнулся со следующей ошибкой:
request = urllib2.Request(whmcsurl,querystring,header) File "/usr/lib64/python2.6/urllib2.py", line 200, in __init__ for key, value in headers.items(): AttributeError: 'str' object has no attribute 'items'
Поэтому я предполагаю, что Python ожидает словарь для заголовка. Но PHP отправляет его как строку.
Могу ли я узнать, как решить эту проблему?
заранее спасибо
Вы слишком сильно себя чувствуете, довольно далеко. Python позаботится о большей части этого для вас. Не нужно открывать сокет самостоятельно, и вам не нужно создавать заголовки и строку открытия HTTP.
Используйте модули urllib
и urllib2
чтобы выполнить эту работу за вас:
from urllib import urlencode from urllib2 import urlopen params = urlencode(postfields) url = whmcsurl + 'modules/servers/licensing/verify.php' response = urlopen(url, params) data = response.read()
urlopen()
принимает второй параметр, данные, отправляемые в запрос POST
; библиотека позаботится о вычислении длины тела и задает соответствующие заголовки. Прежде всего, под капотом он использует другую библиотеку httplib
, чтобы заботиться о соединении сокетов и создавать допустимые заголовки и строку запроса HTTP.
Тело POST кодируется с помощью urllib.urlencode()
, который также заботится о правильном цитировании для вас.
Вы также можете посмотреть в библиотеку внешних requests
, которая еще упрощает использование API:
import requests response = requests.post(whmcsurl + 'modules/servers/licensing/verify.php', params=params) data = response.content # or response.text for decoded content, or response.json(), etc.
ваши заголовки должны выглядеть так:
headers = { "Content-type" : "application/x-www-form-urlencoded" };