-
Notifications
You must be signed in to change notification settings - Fork 11
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
1b9ba5f
commit 4857134
Showing
8 changed files
with
150 additions
and
98 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,43 +1,34 @@ | ||
import pytest | ||
import uvicorn | ||
from anyio import create_task_group, sleep | ||
from anyio import sleep | ||
from httpx_ws import aconnect_ws | ||
from pycrdt import Doc, Map | ||
from websockets import connect | ||
|
||
from pycrdt_websocket import ASGIServer, WebsocketProvider, WebsocketServer | ||
|
||
websocket_server = WebsocketServer(auto_clean_rooms=False) | ||
app = ASGIServer(websocket_server) | ||
|
||
|
||
@pytest.mark.anyio | ||
async def test_asgi(unused_tcp_port): | ||
# server | ||
config = uvicorn.Config("test_asgi:app", port=unused_tcp_port, log_level="info") | ||
server = uvicorn.Server(config) | ||
async with create_task_group() as tg, websocket_server: | ||
tg.start_soon(server.serve) | ||
while not server.started: | ||
await sleep(0) | ||
|
||
# clients | ||
# client 1 | ||
ydoc1 = Doc() | ||
ydoc1["map"] = ymap1 = Map() | ||
ymap1["key"] = "value" | ||
async with connect( | ||
f"ws://localhost:{unused_tcp_port}/my-roomname" | ||
) as websocket1, WebsocketProvider(ydoc1, websocket1): | ||
await sleep(0.1) | ||
|
||
# client 2 | ||
ydoc2 = Doc() | ||
async with connect( | ||
f"ws://localhost:{unused_tcp_port}/my-roomname" | ||
) as websocket2, WebsocketProvider(ydoc2, websocket2): | ||
await sleep(0.1) | ||
|
||
ydoc2["map"] = ymap2 = Map() | ||
assert str(ymap2) == '{"key":"value"}' | ||
|
||
tg.cancel_scope.cancel() | ||
|
||
from pycrdt_websocket import WebsocketProvider | ||
|
||
from utils import Websocket | ||
|
||
|
||
pytestmark = pytest.mark.anyio | ||
|
||
|
||
@pytest.mark.parametrize("yws_server", [{"auto_clean_rooms": False}], indirect=True) | ||
async def test_asgi(yws_server): | ||
port = yws_server | ||
# client 1 | ||
ydoc1 = Doc() | ||
ydoc1["map"] = ymap1 = Map() | ||
ymap1["key"] = "value" | ||
async with aconnect_ws( | ||
f"http://localhost:{port}/my-roomname" | ||
) as websocket1, WebsocketProvider(ydoc1, Websocket(websocket1, "my-roomname")): | ||
await sleep(0.1) | ||
|
||
# client 2 | ||
ydoc2 = Doc() | ||
async with aconnect_ws( | ||
f"http://localhost:{port}/my-roomname" | ||
) as websocket2, WebsocketProvider(ydoc2, Websocket(websocket2, "my-roomname")): | ||
await sleep(0.1) | ||
|
||
ydoc2["map"] = ymap2 = Map() | ||
assert str(ymap2) == '{"key":"value"}' |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
import subprocess | ||
from contextlib import contextmanager | ||
|
||
from anyio import Lock, connect_tcp | ||
|
||
|
||
class Websocket: | ||
def __init__(self, websocket, path: str): | ||
self._websocket = websocket | ||
self._path = path | ||
self._send_lock = Lock() | ||
|
||
@property | ||
def path(self) -> str: | ||
return self._path | ||
|
||
def __aiter__(self): | ||
return self | ||
|
||
async def __anext__(self) -> bytes: | ||
try: | ||
message = await self.recv() | ||
except Exception: | ||
raise StopAsyncIteration() | ||
return message | ||
|
||
async def send(self, message: bytes): | ||
async with self._send_lock: | ||
await self._websocket.send_bytes(message) | ||
|
||
async def recv(self) -> bytes: | ||
b = await self._websocket.receive_bytes() | ||
return bytes(b) | ||
|
||
|
||
@contextmanager | ||
def yjs_client(client_id: int, port: int): | ||
p = subprocess.Popen(["node", f"tests/yjs_client_{client_id}.js", str(port)]) | ||
yield p | ||
p.kill() | ||
|
||
|
||
async def ensure_server_running(host: str, port: int) -> None: | ||
while True: | ||
try: | ||
await connect_tcp(host, port) | ||
except OSError: | ||
pass | ||
else: | ||
break |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters