在 Python 中模拟 HTTP 服务器

问题描述 投票:0回答:5

我正在编写一个 REST 客户端,我需要在测试中模拟 HTTP 服务器。最适合做到这一点的图书馆是什么?如果我可以创建预期的 HTTP 请求并将其与实际进行比较,那就太好了。

python unit-testing http rest mocking
5个回答
10
投票

尝试HTTPretty,Python 的 HTTP 客户端模拟库可帮助您专注于客户端。


9
投票

您还可以自己创建一个小型模拟服务器。 我正在使用一个名为 Flask 的小型网络服务器。

import flask
app = flask.Flask(__name__)

def callback():
    return flask.jsonify(list())

app.add_url_rule("users", view_func=callback)
app.run()

这将在 http://localhost:5000/users 下生成一个服务器,并执行回调函数。

我创建了一个要点来提供带有关闭机制等的工作示例。 https://gist.github.com/eruvanos/f6f62edb368a20aaa880e12976620db8


7
投票

您无需使用任何外部库,只需运行临时 HTTP 服务器即可完成此操作。

例如模拟 https://api.ipify.org?format=json

"""Unit tests for ipify"""

import http.server
import threading
import unittest
import urllib.request


class MockIpifyHTTPRequestHandler(http.server.BaseHTTPRequestHandler):
    """HTTPServer mock request handler"""

    def do_GET(self):  # pylint: disable=invalid-name
        """Handle GET requests"""
        self.send_response(200)
        self.send_header("Content-Type", "application/json")
        self.end_headers()
        self.wfile.write(b'{"ip":"1.2.3.45"}')

    def log_request(self, code=None, size=None):
        """Don't log anything"""


class UnitTests(unittest.TestCase):
    """Unit tests for urlopen"""

    def test_urlopen(self):
        """Test urlopen ipify"""
        server = http.server.ThreadingHTTPServer(
            ("127.0.0.127", 9999), MockIpifyHTTPRequestHandler
        )
        with server:
            server_thread = threading.Thread(target=server.serve_forever)
            server_thread.daemon = True
            server_thread.start()

            request = request = urllib.request.Request("http://127.0.0.127:9999/")
            with urllib.request.urlopen(request) as response:
                result = response.read()
            server.shutdown()

        self.assertEqual(result, b'{"ip":"1.2.3.45"}')

我找到的替代解决方案位于https://stackoverflow.com/a/34929900/15862


0
投票

Mockintosh 似乎是另一种选择。


0
投票

您可以信赖pytest-httpserver

它当场启动一个服务器 - localhost,该服务器在拆卸时关闭。

# the httpserver is a fixture automatically provided by the library
async def test_get_location(httpserver: HTTPServer):
   # setup the expected calls to the server
   httpserver.expect_oneshot_request(
      method="GET",
      uri="/locations/location_123",
   )

   # now you can call httpserver.url_for("/locations/location_123") with any HTTP client
   # IRL you'd inject the base URL (httpserver.url_for("") in your component under test;
   # then you'd call the method under test which would consume the setup calls

超快、干净、真实,并且不涉及任何模拟。

© www.soinside.com 2019 - 2024. All rights reserved.