ChatGPT解决这个技术问题 Extra ChatGPT

在 Python 中 HTTP GET 的最快方法是什么?

如果我知道内容将是一个字符串,那么在 Python 中进行 HTTP GET 的最快方法是什么?我正在搜索文档以获取快速的单行代码,例如:

contents = url.get("http://example.com/foo/bar")

但我使用 Google 能找到的只有 httpliburllib - 我无法在这些库中找到快捷方式。

标准 Python 2.5 是否具有上述某种形式的快捷方式,或者我应该编写一个函数 url_get

我不希望将炮击的输出捕获到 wget 或 curl。

我想我会传递这个,因为它让我难倒了好几个小时。我尝试获取在浏览器中直观显示的文本,但得到了 Web 应用程序的片段。解决方案是进入浏览器开发工具,单击网络选项卡,然后重新加载页面。在通过网络传来的文件列表中,我可以看到我想要的文本文件。我可以右键单击它并“在新选项卡中打开”进行验证。

B
Boris Verkhovskiy

蟒蛇 3:

import urllib.request
contents = urllib.request.urlopen("http://example.com/foo/bar").read()

蟒蛇2:

import urllib2
contents = urllib2.urlopen("http://example.com/foo/bar").read()

urllib.requestread 的文档。


一切都被清理干净了吗?看来我应该在您的 read 之后调用 close。那有必要吗?
关闭它是一种很好的做法,但如果您正在寻找一个快速的单线,您可以省略它。 :-)
由 urlopen 返回的对象将在超出范围时被删除(并最终确定,从而关闭它)。因为 Cpython 是引用计数的,所以您可以依赖 read 之后立即发生的情况。但是对于 Jython 等来说,with 块会更清晰、更安全。
它不适用于仅 HTTPS 的网站。 requests 工作正常
如果您使用的是 Amazon Lambda 并且需要获取 URL,那么 2.x 解决方案是可用的并且是内置的。它似乎也适用于 https。只不过是 r = urllib2.urlopen("http://blah.com/blah") 然后是 text = r.read()。它是同步的,它只是等待“文本”中的结果。
B
Boris Verkhovskiy

使用 Requests 库:

import requests
r = requests.get("http://example.com/foo/bar")

然后你可以做这样的事情:

>>> print(r.status_code)
>>> print(r.headers)
>>> print(r.content)  # bytes
>>> print(r.text)     # r.content as str

通过运行以下命令安装请求:

pip install requests

几乎任何 Python 库都可以在 AWS Lambda 中使用。对于纯 Python,您只需要“供应商”该库(复制到模块的文件夹中,而不是使用 pip install)。对于非纯库,有一个额外的步骤 - 您需要将库 pip install 放到 AWS Linux 的实例上(运行相同的操作系统变体 lambda),然后复制这些文件,以便您与 AWS 具有二进制兼容性Linux。唯一不能在 Lambda 中使用的库是那些只有二进制发行版的库,谢天谢地,这种库非常少见。
@lawphotog 这确实适用于 python3,但您必须pip install requests
甚至 urllib2 标准库也推荐 requests
关于 Lambda:如果您确实希望在 AWS Lambda 函数中使用请求。还有一个预装的 boto3 requests 库。 from botocore.vendored import requests 用法response = requests.get('...')
@kmjb 从 botocore 借用请求已被弃用 aws.amazon.com/blogs/developer/… 并且--imo--依赖间接依赖是个坏主意
M
Manos Nikolaidis

如果您希望使用 httplib2 的解决方案成为 oneliner,请考虑实例化匿名 Http 对象

import httplib2
resp, content = httplib2.Http().request("http://example.com/foo/bar")

h
hennr

看看 httplib2,除了许多非常有用的功能之外,它提供了您想要的东西。

import httplib2

resp, content = httplib2.Http().request("http://example.com/foo/bar")

其中 content 将是响应正文(作为字符串),而 resp 将包含状态和响应标头。

虽然它不包含在标准 python 安装中(但它只需要标准 python),但它绝对值得一试。


佚名

使用强大的 urllib3 库就足够简单了。

像这样导入它:

import urllib3

http = urllib3.PoolManager()

并提出这样的请求:

response = http.request('GET', 'https://example.com')

print(response.data) # Raw data.
print(response.data.decode('utf-8')) # Text.
print(response.status) # Status code.
print(response.headers['Content-Type']) # Content type.

您也可以添加标题:

response = http.request('GET', 'https://example.com', headers={
    'key1': 'value1',
    'key2': 'value2'
})

更多信息可以在 urllib3 documentation 上找到。

urllib3 比内置 urllib.requesthttp 模块更安全、更易于使用,并且稳定。


非常适合您可以轻松提供 HTTP 动词的事实
g
greatvovan

实际上,在 Python 中,我们可以从文件中读取 HTTP 响应,这是从 API 读取 JSON 的示例。

import json
from urllib.request import urlopen

with urlopen(url) as f:
    resp = json.load(f)

return resp['some_key']

尽管我们感谢您的回答,但如果它在其他答案之上提供额外的价值会更好。在这种情况下,您的答案不会提供额外的价值,因为另一个用户已经发布了该解决方案。如果之前的答案对您有帮助,您应该投票而不是重复相同的信息。
这是一个旧的请求/答案,但我发现了它的价值,因为它具有我可以抓住的优雅的 with... 语法。
这个问题增加了价值,因为它使用了 with 结构,该结构在投票最多和接受的答案的评论中得到了很多讨论,但缺乏它。
m
michael_s

无需进一步必要的导入,此解决方案就可以工作(对我而言)- 也可以使用 https:

try:
    import urllib2 as urlreq # Python 2.x
except:
    import urllib.request as urlreq # Python 3.x
req = urlreq.Request("http://example.com/foo/bar")
req.add_header('User-Agent', 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.113 Safari/537.36')
urlreq.urlopen(req).read()

在标题信息中未指定“User-Agent”时,我经常难以抓取内容。然后通常使用以下内容取消请求:urllib2.HTTPError: HTTP Error 403: Forbiddenurllib.error.HTTPError: HTTP Error 403: Forbidden


出乎意料的是,根据 stackoverflow.com/questions/30591706/…,Microsoft Edge 的“用户代理”确实类似于 Mozilla/5.0 (Windows NT 10.0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/42.0.2311.135 Safari/537.36 Edge/12.10136。不知道如何找出最新的 Microsoft Edge UA string,但这里的答案正确地暗示了解决它的方法。
C
Ciro Santilli Путлер Капут 六四事

如何发送标头

蟒蛇 3:

import urllib.request
contents = urllib.request.urlopen(urllib.request.Request(
    "https://api.github.com/repos/cirosantilli/linux-kernel-module-cheat/releases/latest",
    headers={"Accept" : 'application/vnd.github.full+json"text/html'}
)).read()
print(contents)

蟒蛇2:

import urllib2
contents = urllib2.urlopen(urllib2.Request(
    "https://api.github.com",
    headers={"Accept" : 'application/vnd.github.full+json"text/html'}
)).read()
print(contents)

X
Xuan

theller 的 wget 解决方案非常有用,但是,我发现它不会在整个下载过程中打印出进度。如果您在reporthook 中的打印语句之后添加一行,那就完美了。

import sys, urllib

def reporthook(a, b, c):
    print "% 3.1f%% of %d bytes\r" % (min(100, float(a * b) / c * 100), c),
    sys.stdout.flush()
for url in sys.argv[1:]:
    i = url.rfind("/")
    file = url[i+1:]
    print url, "->", file
    urllib.urlretrieve(url, file, reporthook)
print

t
theller

这是 Python 中的 wget 脚本:

# From python cookbook, 2nd edition, page 487
import sys, urllib

def reporthook(a, b, c):
    print "% 3.1f%% of %d bytes\r" % (min(100, float(a * b) / c * 100), c),
for url in sys.argv[1:]:
    i = url.rfind("/")
    file = url[i+1:]
    print url, "->", file
    urllib.urlretrieve(url, file, reporthook)
print

佚名

如果您想要较低级别的 API:

import http.client

conn = http.client.HTTPSConnection('example.com')
conn.request('GET', '/')

resp = conn.getresponse()
content = resp.read()

conn.close()

text = content.decode('utf-8')

print(text)

A
Akshar

优解轩,Theller。

为了让它与 python 3 一起工作,请进行以下更改

import sys, urllib.request

def reporthook(a, b, c):
    print ("% 3.1f%% of %d bytes\r" % (min(100, float(a * b) / c * 100), c))
    sys.stdout.flush()
for url in sys.argv[1:]:
    i = url.rfind("/")
    file = url[i+1:]
    print (url, "->", file)
    urllib.request.urlretrieve(url, file, reporthook)
print

此外,您输入的 URL 应该以“http://”开头,否则会返回未知 url 类型错误。


K
Kimmo

如果您专门使用 HTTP API,还有更方便的选择,例如 Nap

例如,以下是自 2014 年 5 月 1 日以来从 Github 获取要点的方法:

from nap.url import Url
api = Url('https://api.github.com')

gists = api.join('gists')
response = gists.get(params={'since': '2014-05-01T00:00:00Z'})
print(response.json())

更多示例:https://github.com/kimmobrunfeldt/nap#examples


你应该提到你是这个库的作者。
P
Pedro Lobito

对于 python >= 3.6,您可以使用 dload

import dload
t = dload.text(url)

对于 json

j = dload.json(url)

安装:
pip install dload


OP 希望在不使用库的情况下发出 GET 请求,而此解决方案要求您使用 pip 安装包并导入库。
@YılmazAlpaslan OP 没有要求这样的事情,这是有人对我回滚的问题的标题进行的编辑。这个答案的实际问题是它推荐了一些没有人使用的奇怪库。
据我了解,该操作要求“Python 中 HTTP GET 的最快捷方式”,基于此,您可以使用 dload 库,即使没有多少用户使用它,一些这不是答案的要求。只是一个猜测,但我认为您没有正确理解这个问题,但阅读其他答案可能会给您提供线索,因为还推荐了许多不同的库。