在Python脚本中执行curl命令

Kir*_*uri 53 python curl pycurl python-2.7

我试图在python脚本中执行curl命令.

如果我在终端中这样做,它看起来像这样:

curl -X POST -d  '{"nw_src": "10.0.0.1/32", "nw_dst": "10.0.0.2/32", "nw_proto": "ICMP", "actions": "ALLOW", "priority": "10"}' http://localhost:8080/firewall/rules/0000000000000001
Run Code Online (Sandbox Code Playgroud)

我已经看过要使用的建议pycurl,但我无法弄清楚如何将它应用到我的.

我试过用:

subprocess.call([
    'curl',
    '-X',
    'POST',
    '-d',
    flow_x,
    'http://localhost:8080/firewall/rules/0000000000000001'
])
Run Code Online (Sandbox Code Playgroud)

它有效,但还有更好的方法吗?

OJF*_*ord 148

别!

我知道,这是没有人想要的"答案".但是,如果有什么值得做的话,那值得做对,对吗?

这看起来像一个好主意可能源于一个相当广泛的误解,即shell命令,例如curl程序本身以外的任何东西.

所以你要问的是"如何从我的程序中运行这个其他程序,只是为了做一个微不足道的小网页请求?".那太疯狂了,必须有更好的方法吗?

肯定,Uxio的回答是有效的.但它看起来很像Pythonic,是吗?这只是针对一个小请求的大量工作.Python应该是关于飞行的!任何书面可能是希望他们只是call倒是curl!


它有效,但有更好的方法吗?

是的,有一个更好的办法!

请求:人类的HTTP

事情不应该是这样的.不是在Python中.

让我们来看看这个页面:

import requests
res = requests.get('https://stackoverflow.com/questions/26000336')
Run Code Online (Sandbox Code Playgroud)

就是这样,真的!然后你有原始的res.text,或res.json()输出的res.headers,等等.

您可以查看文档(上面链接)以获取设置所有选项的详细信息,因为我认为OP现在已经开始了,而您 - 现在是读者 - 可能需要不同的选项.

但是,例如,它很简单:

url     = 'http://example.tld'
payload = { 'key' : 'val' }
headers = {}
res = requests.post(url, data=payload, headers=headers)
Run Code Online (Sandbox Code Playgroud)

您甚至可以使用漂亮的Python dict在GET请求中提供查询字符串params={}.

简单而优雅.保持冷静,然后飞翔.

  • @Gary`pip安装请求` (11认同)
  • 我正在使用 python 2.4.3。无法使用请求。导入错误:没有名为 requests 的模块。 (2认同)

Uxi*_*xio 33

您可以使用urllib作为@roippi说:

import urllib2
data = '{"nw_src": "10.0.0.1/32", "nw_dst": "10.0.0.2/32", "nw_proto": "ICMP", "actions": "ALLOW", "priority": "10"}'
url = 'http://localhost:8080/firewall/rules/0000000000000001'
req = urllib2.Request(url, data, {'Content-Type': 'application/json'})
f = urllib2.urlopen(req)
for x in f:
    print(x)
f.close()
Run Code Online (Sandbox Code Playgroud)

  • 这取决于子进程,但是当语言有核心库时产生子进程调用命令,这绝对不是正确的方法 (3认同)

hya*_*des 24

如果你没有过多地调整curl命令,你也可以直接调用curl命令

import shlex
cmd = '''curl -X POST -d  '{"nw_src": "10.0.0.1/32", "nw_dst": "10.0.0.2/32", "nw_proto": "ICMP", "actions": "ALLOW", "priority": "10"}' http://localhost:8080/firewall/rules/0000000000000001'''
args = shlex.split(cmd)
process = subprocess.Popen(args, shell=False, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
stdout, stderr = process.communicate()
Run Code Online (Sandbox Code Playgroud)


Nit*_*ain 12

使用此工具(免费托管在此处)将curl命令转换为等效的Python请求代码:

示例:

curl 'https://www.example.com/' -H 'Connection: keep-alive' -H 'Cache-Control: max-age=0' -H 'Origin: https://www.example.com' -H 'Accept-Encoding: gzip, deflate, br' -H 'Cookie: SESSID=ABCDEF' --data-binary 'Pathfinder' --compressed
Run Code Online (Sandbox Code Playgroud)

整洁地转换为:

import requests

cookies = {
    'SESSID': 'ABCDEF',
}

headers = {
    'Connection': 'keep-alive',
    'Cache-Control': 'max-age=0',
    'Origin': 'https://www.example.com',
    'Accept-Encoding': 'gzip, deflate, br',
}

data = 'Pathfinder'

response = requests.post('https://www.example.com/', headers=headers, cookies=cookies, data=data)
Run Code Online (Sandbox Code Playgroud)

  • @OJFord启发了我们为什么不在python中使用curl,而Nitin描绘了使用“请求”实现相同效果的最简单方法。我强烈推荐这个答案。 (3认同)

Ram*_*amy 8

尝试使用子流程

CurlUrl="curl 'https://www.example.com/' -H 'Connection: keep-alive' -H 'Cache- 
          Control: max-age=0' -H 'Origin: https://www.example.com' -H 'Accept-Encoding: 
          gzip, deflate, br' -H 'Cookie: SESSID=ABCDEF' --data-binary 'Pathfinder' -- 
          compressed"
Run Code Online (Sandbox Code Playgroud)

使用getstatusoutput存储结果

status, output = subprocess.getstatusoutput(CurlUrl)
Run Code Online (Sandbox Code Playgroud)


小智 5

您可以使用下面的代码片段

import shlex
import subprocess
import json

def call_curl(curl):
    args = shlex.split(curl)
    process = subprocess.Popen(args, shell=False, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
    stdout, stderr = process.communicate()
    return json.loads(stdout.decode('utf-8'))


if __name__ == '__main__':
    curl = '''curl - X
    POST - d
    '{"nw_src": "10.0.0.1/32", "nw_dst": "10.0.0.2/32", "nw_proto": "ICMP", "actions": "ALLOW", "priority": "10"}'
    http: // localhost: 8080 / firewall / rules / 0000000000000001 '''
    output = call_curl(curl)
    print(output)
Run Code Online (Sandbox Code Playgroud)