microdot — framework HTTP minimal

Microdot este un framework HTTP mic, inspirat de Flask, pentru MicroPython. Rulează peste asyncio, gestionează mai mulți clienți concurenți fără fire de execuție și expune un API familiar bazat pe decoratoare de rute. O aplicație minimală arată astfel:

from microdot import Microdot

app = Microdot()

@app.route('/')
async def index(request):
    return 'Hello, world!'

app.run(host='0.0.0.0', port=80)

class Microdot

class microdot.Microdot

O instanță de aplicație HTTP. O singură instanță este construită aproape de începutul scriptului și decorată cu gestionari de rute; apelarea run() sau așteptarea (await) lui start_server() începe servirea.

Înregistrarea rutelor

route(url_pattern: str, methods: list | None = None) Callable

Decorator care înregistrează un gestionar pentru url_pattern sub metodele HTTP enumerate (implicit ['GET']). Returnează decoratorul care, atunci când este aplicat unei funcții, o înregistrează drept gestionar și returnează funcția nemodificată.

url_pattern

Un șablon de cale. Acceptă segmente statice (/users) și segmente dinamice cuprinse între < / >. Segmentele dinamice acceptă un prefix opțional de tip separat prin :<int:id>, <path:rest>, <re:[0-9a-f]+:hex>. Tipul implicit este string.

methods

Lista numelor de metode HTTP. Dacă este omisă, se potrivește doar GET.

Gestionarul este apelat mai întâi cu obiectul cerere, apoi cu orice segmente dinamice capturate, sub formă de argumente cu cuvânt-cheie. Valoarea returnată de gestionar devine răspunsul HTTP: un Response, un șir de caractere, un tuplu (body, status_code[, headers]) sau un dict / list (trimis ca JSON).

get(url_pattern: str) Callable

Alias de conveniență pentru route(url_pattern, methods=['GET']) – înregistrează funcția decorată drept gestionar GET pentru url_pattern. Returnează decoratorul.

post(url_pattern: str) Callable

Alias de conveniență pentru route(url_pattern, methods=['POST']) – înregistrează funcția decorată drept gestionar POST pentru url_pattern. Returnează decoratorul.

put(url_pattern: str) Callable

Alias de conveniență pentru route(url_pattern, methods=['PUT']) – înregistrează funcția decorată drept gestionar PUT pentru url_pattern. Returnează decoratorul.

patch(url_pattern: str) Callable

Alias de conveniență pentru route(url_pattern, methods=['PATCH']) – înregistrează funcția decorată drept gestionar PATCH pentru url_pattern. Returnează decoratorul.

delete(url_pattern: str) Callable

Alias de conveniență pentru route(url_pattern, methods=['DELETE']) – înregistrează funcția decorată drept gestionar DELETE pentru url_pattern. Returnează decoratorul.

Cârlige de ciclu de viață

before_request(f: Callable) Callable

Decorator care înregistrează f pentru a rula înaintea fiecărei cereri. f primește obiectul cerere; valoarea sa returnată este în mod normal ignorată. Pentru a scurtcircuita cererea, returnați un Response (sau o valoare care se convertește la unul) – restul fluxului este atunci ocolit, iar acel răspuns este trimis. Returnează f nemodificat.

after_request(f: Callable) Callable

Decorator care înregistrează f pentru a rula după fiecare cerere reușită. f primește (request, response) și trebuie să returneze obiectul răspuns (eventual modificat). Returnează f nemodificat.

after_error_request(f: Callable) Callable

Decorator care înregistrează f pentru a rula după ce Microdot generează un răspuns de eroare (404, 500, excepție ridicată etc.). f primește (request, response) și trebuie să returneze obiectul răspuns (eventual modificat). Returnează f nemodificat.

errorhandler(status_code_or_exception_class) Callable

Decorator care înregistrează un gestionar personalizat pentru un cod de stare HTTP sau o clasă de excepție Python. Pentru codurile de stare, gestionarul primește doar cererea; pentru clasele de excepție, (request, exception). Returnează decoratorul.

Montare și abandonare

mount(subapp: Microdot, url_prefix: str = '', local: bool = False) None

Atașează rutele unei alte instanțe Microdot sub url_prefix. Când local este False (implicit), gestionarii before / after / error ai sub-aplicației sunt de asemenea atașați la cea părinte. Când este True, acei gestionari rulează doar pentru rutele sub-aplicației. Returnează None.

static abort(status_code: int, reason: str | None = None) None

Ridicați HTTPException pentru a abandona cererea curentă cu codul de stare dat. Nu returnează niciodată normal – framework-ul prinde excepția și o transformă în răspunsul de eroare corespunzător. Convenabil în interiorul corpurilor de rută:

from microdot import abort

@app.get('/users/<int:id>')
def get_user(request, id):
    user = lookup(id)
    if user is None:
        abort(404)
    return user.to_dict()

Rularea serverului

run(host: str = '0.0.0.0', port: int = 5000, debug: bool = False, ssl=None) None

Blochează firul apelant, rulează asyncio.run() pe start_server(). Returnează None doar după ce shutdown() a fost apelat și bucla de ascultare se încheie. Cel mai simplu mod de a lansa o aplicație de sine stătătoare:

app.run(host='0.0.0.0', port=80)
async start_server(host: str = '0.0.0.0', port: int = 5000, debug: bool = False, ssl=None, start_serving: bool = True) None

Pornește serverul ca o corutină. Folosiți acest lucru când integrați cu o buclă de evenimente asyncio existentă, alături de alte sarcini. Corutina nu returnează până când shutdown() nu este apelat:

async def main():
    await asyncio.gather(
        app.start_server(port=80),
        capture_loop(),
    )
host

Interfața de rețea pe care se ascultă. '0.0.0.0' (implicit) înseamnă toate interfețele; '127.0.0.1' înseamnă doar loopback.

port

Portul TCP pe care se ascultă. Implicit 5000 – alegeți 80 pentru HTTP simplu, 443 pentru HTTPS.

debug

Dacă este True, înregistrează fiecare cerere și descarcă urmele de stivă (tracebacks) la stdout.

ssl

Un ssl.SSLContext pentru a împacheta conexiunile primite în TLS. None (implicit) înseamnă HTTP simplu.

start_serving

Relevant doar pe CPython; ignorat pe MicroPython.

shutdown() None

Solicită o oprire grațioasă a serverului. Sigur de apelat dintr-un gestionar de rută – cererea curentă se finalizează înainte ca bucla să se încheie. Returnează imediat; oprirea efectivă are loc odată ce cererea în curs se finalizează.

Atribute

url_map: list

Lista rutelor înregistrate sub formă de tupluri (methods, URLPattern, handler, url_prefix, subapp).

before_request_handlers: list

Lista apelabilelor înregistrate cu before_request(), în ordinea înregistrării. Fiecare rulează cu obiectul cerere înaintea gestionarului de rută. Mutarea directă a listei funcționează, dar este rareori necesară – preferați decoratorul.

after_request_handlers: list

Lista apelabilelor înregistrate cu after_request(), în ordinea înregistrării. Fiecare rulează cu (request, response) după o cerere reușită și trebuie să returneze răspunsul (eventual modificat).

after_error_request_handlers: list

Lista apelabilelor înregistrate cu after_error_request(), în ordinea înregistrării. Fiecare rulează cu (request, response) după ce este generat un răspuns de eroare (de către framework sau de către un gestionar de erori al aplicației) și trebuie să returneze răspunsul.

error_handlers: dict

Mapare a cheilor de eroare către apelabile gestionare, populată de errorhandler(). Cheile sunt fie coduri de stare HTTP (int), fie clase de excepție Python; valorile sunt gestionarii înregistrați. Gestionarii de coduri de stare primesc (request); gestionarii de clase de excepție primesc (request, exception).

debug: bool

True cât timp serverul rulează cu debug=True.

class Request

class microdot.Request

O cerere HTTP primită. Instanțele sunt transmise gestionarilor de rută drept primul argument pozițional. Aplicațiile nu construiesc Request direct.

Atribute de clasă

max_content_length: int

Respinge cererile al căror Content-Length depășește acest număr de octeți, cu un răspuns 413. Implicit 16 KB.

max_body_length: int

Cel mai mare corp care este stocat în memorie și expus prin body. Corpurile mai mari (până la max_content_length) rămân pe socket și trebuie citite prin stream. Implicit 16 KB.

max_readline: int

Lungimea maximă a unei singure linii de cerere / linii de antet, în octeți. Implicit 2 KB.

Atribute de instanță

app: Microdot

Instanța Microdot care gestionează cererea.

client_addr: tuple

Adresa clientului sub formă de (host, port).

method: str

Șirul metodei HTTP ('GET', 'POST', …).

scheme: str

'http' sau 'https'.

url: str

Calea completă a URL-ului cererii și șirul de interogare (tot ce urmează după gazdă).

path: str

Doar porțiunea de cale.

query_string: str | None

Porțiunea brută a șirului de interogare sau None.

args: MultiDict

Șirul de interogare analizat sub formă de MultiDict.

headers: NoCaseDict

Antetele cererii sub formă de NoCaseDict (căutare insensibilă la majuscule).

cookies: dict

Antetul Cookie analizat sub formă de dict.

content_length: int

Valoarea întreagă Content-Length sau 0 dacă lipsește.

content_type: str | None

Valoarea antetului Content-Type sau None.

g: object

Un container liber per cerere (un obiect simplu). Atribuiți-i atribute pentru a transmite valori între cârlige și gestionari (request.g.user = ...).

route: Callable

Funcția gestionar care s-a potrivit cu această cerere.

url_prefix: str

Prefixul sub care a fost montată ruta sau ''.

subapp: Microdot | None

Instanța sub-aplicației montate sau None.

Accesul la corp

body: bytes

Corpul complet al cererii sub formă de bytes. Gol când corpul este transmis în flux (vedeți stream).

stream: object

Un obiect flux asincron care expune read() peste corp. Folosiți acest lucru pentru corpuri mai mari decât max_body_length.

json: dict | list | str | int | float | bool | None

Corpul analizat ca JSON (un dict, list, str, int, float sau bool – orice codifică sarcina utilă) sau None dacă Content-Type nu este application/json.

form: MultiDict | None

Câmpurile de formular codificate în URL sub formă de MultiDict sau None. Pentru multipart/form-data, decorați ruta cu microdot.multipart.with_form_data().

files: dict | None

Fișierele încărcate sub formă de {name: FileUpload}, populate de microdot.multipart.with_form_data(). None până când rulează acel decorator.

after_request(f: Callable) Callable

Înregistrează un cârlig after-request local cererii – rulează după gestionarii after-request la nivel de aplicație, doar la succes. f primește (request, response) și trebuie să returneze obiectul răspuns (eventual modificat). Returnează f nemodificat.

class Response

class microdot.Response(body=b'', status_code: int = 200, headers: dict | None = None, reason: str | None = None)

Un răspuns HTTP. Majoritatea gestionarilor returnează valori pe care Microdot le convertește automat la un Response; construiți unul direct când aveți nevoie de antete personalizate sau de un cod de stare specific.

body

Corpul răspunsului. str este codificat în UTF-8; dict / list este codificat în JSON și Content-Type este setat corespunzător; bytes este trimis ca atare; un obiect de tip fișier sau un generator asincron este transmis în flux.

status_code

Cod de stare HTTP numeric. Implicit 200.

headers

Dict de antete de răspuns (insensibil la majuscule).

reason

Frază de motiv personalizată. Implicit "OK" pentru 200 și "N/A" în caz contrar.

Atribute de clasă

default_content_type: str

Content-Type folosit când niciunul nu este setat explicit. Implicit 'text/plain'.

default_send_file_max_age: int | None

Valoarea Cache-Control: max-age pentru send_file() când max_age nu este dat. None (implicit) înseamnă fără antet Cache-Control.

send_file_buffer_size: int

Dimensiunea bucății pentru transmiterea în flux a send_file(). Implicit 1024.

already_handled: None

Santinelă returnată de gestionarii care au scris deja răspunsul direct (folosită de actualizările WebSocket). Întotdeauna None; identitatea este cea care contează.

types_map: dict

Mapare extensie-la-tip-mime folosită de send_file() pentru deducerea tipului de conținut. Mapează css, gif, html, jpg, js, json, png, txt, svg.

Metode

Adaugă un antet Set-Cookie. expires poate fi un șir preformatat sau un obiect de tip datetime cu timetuple(). Returnează None; antetul este adăugat acestui răspuns pe loc.

Setează un Set-Cookie care expiră cookie-ul dat imediat. kwargs acceptă aceleași opțiuni ca set_cookie() (path, domain, secure, http_only, partitioned); expires și max_age sunt ignorate. Returnează None; antetul este adăugat acestui răspuns pe loc.

classmethod redirect(location: str, status_code: int = 302) Response

Returnează un răspuns de redirecționare:

@app.get('/old')
def old(request):
    return Response.redirect('/new')
classmethod send_file(filename: str, status_code: int = 200, content_type: str | None = None, stream=None, max_age: int | None = None, compressed: bool | str = False, file_extension: str = '') Response

Transmite în flux un fișier din sistemul de fișiere drept corpul răspunsului. content_type este dedus din extensie prin types_map dacă nu este dat. compressed=True setează Content-Encoding: gzip (fișierul trebuie să fie deja comprimat).

Atenționare

filename este deschis direct. Nu transmiteți niciodată o cale nesanitizată furnizată de utilizator – a face acest lucru permite dezvăluirea arbitrară a fișierelor.

Excepții

exception microdot.HTTPException

Ridicată de abort() pentru a scurtcircuita o cerere cu un cod de stare specific. Microdot prinde acest lucru și îl transformă în răspunsul de eroare corespunzător.

status_code: int

Codul de stare HTTP numeric de returnat – valoarea transmisă lui abort().

reason: str

Fraza de motiv de inclus în răspunsul de eroare. Dacă nu este dată lui abort(), implicit este "<status_code> error" (de ex. "404 error").

class URLPattern

class microdot.URLPattern(url_pattern: str)

Forma compilată a șablonului de URL al unei rute. Construită automat de Microdot.route(); aplicațiile rareori instanțiază una direct.

classmethod register_type(type_name: str, pattern: str = '[^/]+', parser: Callable | None = None) None

Înregistrează un nou tip de segment dinamic pentru utilizare în șabloanele de rută. Returnează None; tipul este adăugat în registrul de tipuri la nivel de clasă. De exemplu, pentru a adăuga un tip <uuid:...>

URLPattern.register_type('uuid', '[0-9a-f-]{36}')

parser este un apelabil opțional care convertește șirul capturat înainte ca acesta să ajungă la gestionar.

match(path: str) dict | None

Potrivește path cu șablonul și returnează un dict de grupuri capturate sau None dacă nu există potrivire.

Clase auxiliare

class microdot.MultiDict(initial_dict: dict | None = None)

O subclasă de dict care stochează mai multe valori per cheie. Folosită pentru șiruri de interogare și corpuri de formular codificate în URL, unde aceeași cheie poate apărea de mai multe ori (?tag=a&tag=b).

get(key, default=None, type: Callable | None = None)

Returnează prima valoare pentru key, opțional convertită cu type (un apelabil). Returnează default dacă cheia lipsește sau conversia eșuează; în caz contrar returnează valoarea (eventual convertită).

getlist(key, type: Callable | None = None) list

Returnează toate valorile pentru key sub formă de listă, opțional cu fiecare valoare convertită de type. Returnează o listă goală dacă key nu este prezentă.

class microdot.NoCaseDict

O subclasă de dict cu chei de tip șir insensibile la majuscule. Folosită pentru Request.headers și Response.headers.

Funcții la nivel de modul

microdot.abort(status_code: int, reason: str | None = None) None

Scurtătură pentru Microdot.abort(). Nu returnează niciodată normal – ridică HTTPException. Importabilă ca from microdot import abort.

microdot.redirect(location: str, status_code: int = 302) Response

Scurtătură pentru Response.redirect(). Importabilă ca from microdot import redirect.

microdot.send_file(filename: str, **kwargs) Response

Scurtătură pentru Response.send_file().

microdot.urlencode(s: str) str

Codifică în procente o componentă de URL. Înlocuiește caracterele care au semnificație rezervată într-un URL (/, ?, &, =, #, spațiu, …) cu secvențele lor de escape hexazecimale %xx, astfel încât rezultatul să poată sta în siguranță în interiorul unui segment de cale sau al unei valori de interogare. Returnează str-ul codificat.

microdot.urldecode(s: str) str

Decodifică din procente o componentă de URL – inversul lui urlencode(). Secvențele de escape %xx sunt înlocuite cu octetul pe care îl codifică, iar + este convertit într-un spațiu (convenția istorică a șirurilor de interogare). Returnează str-ul decodificat.

Submodule