async def app(event_loop, db, request): globalregistry.reset() settings = get_db_settings(request.node) app = make_app(settings=settings, loop=event_loop) server_settings = settings.get("test_server_settings", {}) host = server_settings.get("host", "127.0.0.1") port = int(server_settings.get("port", 8000)) from uvicorn import Config, Server config = Config(app, host=host, port=port, lifespan="on") server = Server(config=config) task = asyncio.ensure_future(server.serve(), loop=event_loop) while app.app is None and not task.done(): # Wait for app initialization await asyncio.sleep(0.05) if task.done(): task.result() await _clear_dbs(app.app.root) yield host, port server.should_exit = True await asyncio.sleep(1) # There is no other way to wait for server shutdown clear_task_vars()
def test_fragmentation(): def receive_all(sock): chunks = [] while True: chunk = sock.recv(1024) if not chunk: break chunks.append(chunk) return b"".join(chunks) app = Response("Hello, world", media_type="text/plain") def send_fragmented_req(path): sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) sock.connect(("127.0.0.1", 8000)) d = ( f"GET {path} HTTP/1.1\r\n" "Host: localhost\r\n" "Connection: close\r\n\r\n" ).encode() split = len(path) // 2 sock.sendall(d[:split]) time.sleep(0.01) sock.sendall(d[split:]) resp = receive_all(sock) # see https://github.com/kmonsoor/py-amqplib/issues/45 # we skip the error on bsd systems if python is too slow try: sock.shutdown(socket.SHUT_RDWR) except Exception: # pragma: no cover pass sock.close() return resp config = Config(app=app, http="httptools") server = Server(config=config) t = threading.Thread(target=server.run) t.daemon = True t.start() time.sleep(1) # wait for uvicorn to start path = "/?param=" + "q" * 10 response = send_fragmented_req(path) bad_response = b"HTTP/1.1 400 Bad Request" assert bad_response != response[: len(bad_response)] server.should_exit = True t.join()