Skip to content

Commit 12b76dd

Browse files
committed
Improve test coverage of endpoint decorator
I test for an error condition, and also test using the endpoint functions not via HTTP. It was necessary to add a default value for Thing.path to make sure we raise the right error - this is needed by other checks that are introduced in #180.
1 parent 1490501 commit 12b76dd

File tree

2 files changed

+33
-8
lines changed

2 files changed

+33
-8
lines changed

src/labthings_fastapi/thing.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,7 @@ class Thing:
7777
"""A human-readable description of the Thing"""
7878
_labthings_blocking_portal: Optional[BlockingPortal] = None
7979
"""See :ref:`concurrency` for why blocking portal is needed."""
80-
path: Optional[str]
80+
path: Optional[str] = None
8181
"""The path at which the `.Thing` is exposed over HTTP."""
8282

8383
async def __aenter__(self) -> Self:

tests/test_endpoint_decorator.py

Lines changed: 32 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,39 +1,64 @@
11
from fastapi.testclient import TestClient
2-
from labthings_fastapi import ThingServer, Thing, fastapi_endpoint
32
from pydantic import BaseModel
3+
import pytest
4+
import labthings_fastapi as lt
45

56

67
class PostBodyModel(BaseModel):
78
a: int
89
b: int
910

1011

11-
class TestThing(Thing):
12-
@fastapi_endpoint("get")
12+
class MyThing(lt.Thing):
13+
@lt.fastapi_endpoint("get")
1314
def path_from_name(self) -> str:
1415
return "path_from_name"
1516

16-
@fastapi_endpoint("get", path="path_from_path")
17+
@lt.fastapi_endpoint("get", path="path_from_path")
1718
def get_method(self) -> str:
1819
return "get_method"
1920

20-
@fastapi_endpoint("post", path="path_from_path")
21+
@lt.fastapi_endpoint("post", path="path_from_path")
2122
def post_method(self, body: PostBodyModel) -> str:
2223
return f"post_method {body.a} {body.b}"
2324

2425

2526
def test_endpoints():
26-
server = ThingServer()
27-
server.add_thing(TestThing(), "/thing")
27+
"""Check endpoints may be added to the app and work as expected."""
28+
server = lt.ThingServer()
29+
thing = MyThing()
30+
server.add_thing(thing, "/thing")
2831
with TestClient(server.app) as client:
32+
# Check the function works when used directly
33+
assert thing.path_from_name() == "path_from_name"
34+
# Check it works identically over HTTP. The path is
35+
# generated from the name of the function.
2936
r = client.get("/thing/path_from_name")
3037
r.raise_for_status()
3138
assert r.json() == "path_from_name"
3239

40+
# get_method has an explicit path - check it can be
41+
# used both directly and via that path.
42+
assert thing.get_method() == "get_method"
3343
r = client.get("/thing/path_from_path")
3444
r.raise_for_status()
3545
assert r.json() == "get_method"
3646

47+
# post_method uses the same path, for a different
48+
# function
49+
assert thing.post_method(PostBodyModel(a=1, b=2)) == "post_method 1 2"
3750
r = client.post("/thing/path_from_path", json={"a": 1, "b": 2})
3851
r.raise_for_status()
3952
assert r.json() == "post_method 1 2"
53+
54+
55+
def test_endpoint_notconnected(mocker):
56+
"""Check for the correct error if we add endpoints prematurely.
57+
58+
We should get this error if we call ``add_to_fastapi`` on an endpoint
59+
where the `.Thing` does not have a valid ``path`` attribute.
60+
"""
61+
thing = MyThing()
62+
63+
with pytest.raises(lt.exceptions.NotConnectedToServerError):
64+
MyThing.get_method.add_to_fastapi(mocker.Mock(), thing)

0 commit comments

Comments
 (0)