mirror of https://github.com/encode/starlette.git
Version 0.1.3
This commit is contained in:
parent
6334642731
commit
4f80753cf7
52
README.md
52
README.md
|
@ -1,6 +1,6 @@
|
||||||
<p align="center">
|
<h1 align="center">
|
||||||
<h1 align="center">Starlette</h1>
|
Starlette
|
||||||
</p>
|
</h1>
|
||||||
<p align="center">
|
<p align="center">
|
||||||
<em>✨ The little ASGI library that shines. ✨</em>
|
<em>✨ The little ASGI library that shines. ✨</em>
|
||||||
</p>
|
</p>
|
||||||
|
@ -20,7 +20,7 @@
|
||||||
|
|
||||||
Starlette is a small library for working with [ASGI](https://asgi.readthedocs.io/en/latest/).
|
Starlette is a small library for working with [ASGI](https://asgi.readthedocs.io/en/latest/).
|
||||||
|
|
||||||
It gives you `Request` and `Response` classes, a test client, and a
|
It gives you `Request` and `Response` classes, routing, a test client, and a
|
||||||
decorator for writing super-minimal applications.
|
decorator for writing super-minimal applications.
|
||||||
|
|
||||||
**Requirements:**
|
**Requirements:**
|
||||||
|
@ -221,6 +221,48 @@ raise an error.
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
|
## Routing
|
||||||
|
|
||||||
|
Starlette includes a `Router` class which is an ASGI application that
|
||||||
|
dispatches to other ASGI applications.
|
||||||
|
|
||||||
|
```python
|
||||||
|
from starlette import Router, Path, PathPrefix
|
||||||
|
from myproject import Homepage, StaticFiles
|
||||||
|
|
||||||
|
|
||||||
|
app = Router([
|
||||||
|
Path('/', app=Homepage, methods=['GET']),
|
||||||
|
PathPrefix('/static', app=StaticFiles, methods=['GET'])
|
||||||
|
])
|
||||||
|
```
|
||||||
|
|
||||||
|
Paths can use URI templating style to capture path components.
|
||||||
|
|
||||||
|
```python
|
||||||
|
Path('/users/{username}', app=User, methods=['GET'])
|
||||||
|
```
|
||||||
|
|
||||||
|
Path components are made available in the scope, as `scope["kwargs"]`.
|
||||||
|
|
||||||
|
Because each target of the router is an ASGI instance itself, routers
|
||||||
|
allow for easy composition. For example:
|
||||||
|
|
||||||
|
```python
|
||||||
|
app = Router([
|
||||||
|
Path('/', app=Homepage, methods=['GET']),
|
||||||
|
PathPrefix('/users', app=Router([
|
||||||
|
Path('/', app=Users, methods=['GET', 'POST']),
|
||||||
|
Path('/{username}', app=User, methods=['GET']),
|
||||||
|
]))
|
||||||
|
])
|
||||||
|
```
|
||||||
|
|
||||||
|
The router will respond with "404 Not found" or "406 Method not allowed"
|
||||||
|
responses for requests which do not match.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
## Test Client
|
## Test Client
|
||||||
|
|
||||||
The test client allows you to make requests against your ASGI application,
|
The test client allows you to make requests against your ASGI application,
|
||||||
|
@ -264,4 +306,4 @@ async def app(request):
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
<p align="center"><i>API Star is <a href="https://github.com/tomchristie/apistar/blob/master/LICENSE.md">BSD licensed</a> code.<br/>Designed & built in Brighton, England.</i><br/>— ⭐️ —</p>
|
<p align="center"><i>Starlette is <a href="https://github.com/tomchristie/starlette/blob/master/LICENSE.md">BSD licensed</a> code.<br/>Designed & built in Brighton, England.</i><br/>— ⭐️ —</p>
|
||||||
|
|
|
@ -9,9 +9,12 @@ __all__ = (
|
||||||
"asgi_application",
|
"asgi_application",
|
||||||
"HTMLResponse",
|
"HTMLResponse",
|
||||||
"JSONResponse",
|
"JSONResponse",
|
||||||
|
"Path",
|
||||||
|
"PathPrefix",
|
||||||
"Response",
|
"Response",
|
||||||
|
"Router",
|
||||||
"StreamingResponse",
|
"StreamingResponse",
|
||||||
"Request",
|
"Request",
|
||||||
"TestClient",
|
"TestClient",
|
||||||
)
|
)
|
||||||
__version__ = "0.1.2"
|
__version__ = "0.1.3"
|
||||||
|
|
|
@ -20,7 +20,7 @@ class Path(Route):
|
||||||
self.app = app
|
self.app = app
|
||||||
self.methods = methods
|
self.methods = methods
|
||||||
regex = "^" + path + "$"
|
regex = "^" + path + "$"
|
||||||
regex = re.sub("{([a-zA-Z_][a-zA-Z0-9_]*)}", r"(?P<\1>[^/]*)", regex)
|
regex = re.sub("{([a-zA-Z_][a-zA-Z0-9_]*)}", r"(?P<\1>[^/]+)", regex)
|
||||||
self.path_regex = re.compile(regex)
|
self.path_regex = re.compile(regex)
|
||||||
|
|
||||||
def matches(self, scope: Scope) -> typing.Tuple[bool, Scope]:
|
def matches(self, scope: Scope) -> typing.Tuple[bool, Scope]:
|
||||||
|
|
|
@ -14,12 +14,19 @@ def user(scope):
|
||||||
return Response(content, media_type="text/plain")
|
return Response(content, media_type="text/plain")
|
||||||
|
|
||||||
|
|
||||||
|
def staticfiles(scope):
|
||||||
|
return Response("xxxxx", media_type="image/png")
|
||||||
|
|
||||||
|
|
||||||
app = Router(
|
app = Router(
|
||||||
[
|
[
|
||||||
Path("/", app=homepage),
|
Path("/", app=homepage, methods=['GET']),
|
||||||
PathPrefix(
|
PathPrefix(
|
||||||
"/users", app=Router([Path("", app=users), Path("/{username}", app=user)])
|
"/users", app=Router([Path("", app=users), Path("/{username}", app=user)])
|
||||||
),
|
),
|
||||||
|
PathPrefix(
|
||||||
|
"/static", app=staticfiles, methods=['GET']
|
||||||
|
),
|
||||||
]
|
]
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -31,6 +38,10 @@ def test_router():
|
||||||
assert response.status_code == 200
|
assert response.status_code == 200
|
||||||
assert response.text == "Hello, world"
|
assert response.text == "Hello, world"
|
||||||
|
|
||||||
|
response = client.post("/")
|
||||||
|
assert response.status_code == 406
|
||||||
|
assert response.text == "Method not allowed"
|
||||||
|
|
||||||
response = client.get("/foo")
|
response = client.get("/foo")
|
||||||
assert response.status_code == 404
|
assert response.status_code == 404
|
||||||
assert response.text == "Not found"
|
assert response.text == "Not found"
|
||||||
|
@ -42,3 +53,11 @@ def test_router():
|
||||||
response = client.get("/users/tomchristie")
|
response = client.get("/users/tomchristie")
|
||||||
assert response.status_code == 200
|
assert response.status_code == 200
|
||||||
assert response.text == "User tomchristie"
|
assert response.text == "User tomchristie"
|
||||||
|
|
||||||
|
response = client.get("/static/123")
|
||||||
|
assert response.status_code == 200
|
||||||
|
assert response.text == "xxxxx"
|
||||||
|
|
||||||
|
response = client.post("/static/123")
|
||||||
|
assert response.status_code == 406
|
||||||
|
assert response.text == "Method not allowed"
|
||||||
|
|
Loading…
Reference in New Issue