ASGI Middleware for serving Static File.
Project description
ASGIMiddlewareStaticFile
ASGI Middleware for serving static file.
Why?
ASGIMiddlewareStaticFile is a solution when we need to distribute the whole project with static files in Docker; when the deployment environment has very limited resources.
Features
- Standard ASGI middleware implement
- Async file IO
- Support ETag(base on md5(file_size + last_modified) )
Install
pip3 install -U ASGIMiddlewareStaticFile
Usage
Pure ASGI
Code demo_pure_asgi.py
import os from asgi_middleware_static_file import ASGIMiddlewareStaticFile BASE_DIR = os.path.dirname(__name__) STATIC_DIRS = [os.path.join(BASE_DIR, 'demo_static')] async def app(scope, receive, send): assert scope['type'] == 'http' await send({ 'type': 'http.response.start', 'status': 200, 'headers': [ [b'content-type', b'text/plain'], ], }) await send({ 'type': 'http.response.body', 'body': b'Hello, world!', }) app = ASGIMiddlewareStaticFile( app, static_url='static', static_root_paths=STATIC_DIRS )
Run Server
(venv) ➜ asgi-middleware-static-file git:(master) ✗ uvicorn demo_pure_asgi:app INFO: Started server process [21061] INFO: Waiting for application startup. INFO: ASGI 'lifespan' protocol appears unsupported. INFO: Application startup complete. INFO: Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit) INFO: 127.0.0.1:54529 - "GET /static/DEMO HTTP/1.1" 200 OK
Run wget
(venv) ➜ asgi-middleware-static-file git:(master) ✗ wget http://127.0.0.1:8000/static/DEMO --2021-01-11 19:54:24-- http://127.0.0.1:8000/static/DEMO 正在连接 127.0.0.1:8000... 已连接。 已发出 HTTP 请求,正在等待回应... 200 OK 长度:26 [] 正在保存至: “DEMO.6” DEMO.6 100%[==============================================>] 26 --.-KB/s 用时 0s 2021-01-11 19:54:24 (540 KB/s) - 已保存 “DEMO.6” [26/26])
Django
Update file example/django_example/django_example/asgi.py
""" ASGI config for django_example project. It exposes the ASGI callable as a module-level variable named ``application``. For more information on this file, see https://docs.djangoproject.com/en/3.1/howto/deployment/asgi/ """ import os from django.conf import settings from django.core.asgi import get_asgi_application from asgi_middleware_static_file import ASGIMiddlewareStaticFile os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'django_example.settings') application = get_asgi_application() application = ASGIMiddlewareStaticFile( application, static_url=settings.STATIC_URL, static_root_paths=[settings.STATIC_ROOT] )
Do't forget execute
python manage.py collectstatic 133 static files copied to '/Users/rex/p/asgi-middleware-static-file/example/django_example/staticfiles'.
Run server
uvicorn django_example.asgi:application INFO: Started server process [93869] INFO: Waiting for application startup. INFO: ASGI 'lifespan' protocol appears unsupported. INFO: Application startup complete. INFO: Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit) INFO: 127.0.0.1:61925 - "GET /static/DEMO.txt HTTP/1.1" 200 OK
Quart (Flask like)
Code demo_quart.py
import os from quart import Quart from asgi_middleware_static_file import ASGIMiddlewareStaticFile BASE_DIR = os.path.dirname(__name__) STATIC_DIRS = [os.path.join(BASE_DIR, 'demo_static')] app = Quart(__name__) @app.route('/') async def hello(): return 'hello' app = ASGIMiddlewareStaticFile( app, static_url='static', static_root_paths=STATIC_DIRS )
Run Server
(venv) ➜ asgi-middleware-static-file git:(master) ✗ uvicorn demo_quart:app INFO: Started server process [22289] INFO: Waiting for application startup. INFO: Application startup complete. INFO: Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit) INFO: 127.0.0.1:56191 - "GET / HTTP/1.1" 200 OK INFO: 127.0.0.1:56212 - "GET /static/DEMO HTTP/1.1" 200 OK
Run wget
(venv) ➜ asgi-middleware-static-file git:(master) ✗ wget http://127.0.0.1:8000/static/DEMO --2021-01-11 20:17:46-- http://127.0.0.1:8000/static/DEMO 正在连接 127.0.0.1:8000... 已连接。 已发出 HTTP 请求,正在等待回应... 200 OK 长度:26 [] 正在保存至: “DEMO.7” DEMO.7 100%[==============================================>] 26 --.-KB/s 用时 0s 2021-01-11 20:17:46 (1.46 MB/s) - 已保存 “DEMO.7” [26/26])
Alternative
-
ASGI Middleware
- django.contrib.staticfiles.handlers.ASGIStaticFilesHandler
-
WSGI Middleware
-
View
- starlette.staticfiles.StaticFiles
TODO
- zero copy
- file extension filter,
- Cache Control
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Filename, size | File type | Python version | Upload date | Hashes |
---|---|---|---|---|
Filename, size ASGIMiddlewareStaticFile-0.3.1-py2.py3-none-any.whl (6.4 kB) | File type Wheel | Python version py2.py3 | Upload date | Hashes View |
Filename, size ASGIMiddlewareStaticFile-0.3.1.tar.gz (7.6 kB) | File type Source | Python version None | Upload date | Hashes View |
Close
Hashes for ASGIMiddlewareStaticFile-0.3.1-py2.py3-none-any.whl
Algorithm | Hash digest | |
---|---|---|
SHA256 | 01051739913e87b864841f343109de5de7585164c4ffa6f65f0c11700691a596 |
|
MD5 | b6ffb113e9b66dc07d64dc905595e0f8 |
|
BLAKE2-256 | e16a36f85531e247f586c202ff16b6326f5ee1c7c284d37d72f348f6daee6251 |
Close
Hashes for ASGIMiddlewareStaticFile-0.3.1.tar.gz
Algorithm | Hash digest | |
---|---|---|
SHA256 | c28e1d7f1e2bd12947789fe8c3022cabdd8cdd81cfbb3536bbf68cbd8a9af52a |
|
MD5 | 208c9b8c2ac1b77c28fb9235d4f4dd00 |
|
BLAKE2-256 | 71092611c80781c5dd5770fb239219012305c9a7085c09230426984b9d7584be |