विषय पर बढ़ें

मिडलवेयर

te में व्यवहार जोड़ने के लिए कई मिडलवेयर कक्षाएं हैं जो पूरे एप्लिकेशन पर लागू होती हैं। इन्हें मानक ASGI मिडलवेयर कक्षाओं के रूप में लागू किया जाता है और इसे te या किसी अन्य ASGI एप्लिकेशन पर लागू किया जा सकता है।

मिडलवेयर का उपयोग करें

te एप्लिकेशन क्लास आपको ASGI मिडलवेयर को एक तरह से शामिल करने की अनुमति देता है जो यह सुनिश्चित करता है कि यह हमेशा अपवाद हैंडलर द्वारा लपेटा जाता है।

te.से आयात
te.leसे मिडलवेयर आयात
te.le.htpsreसे आयात HTTPSRedirectMiddleware
te.le.edआयात TrustedHostMiddleware

मार्ग = ...

# सुनिश्चित करें कि सभी अनुरोधों में एक example.com 'या
# '*। example.com हेडर होस्ट करें, और http-only एक्सेस को सख्ती से लागू करें।
मिडलवेयर = [
    मिडलवेयर (
        TrustedHostMiddleware
        अनुमति_होस्ट्स = example.com ',' *। example.com '],
    ),
    मिडलवेयर (HTTPSRedirectMiddleware)
]

ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

डिफ़ॉल्ट रूप से, प्रत्येक te एप्लिकेशन में स्वचालित रूप से मिडलवेयर के दो टुकड़े शामिल हैं:

  • ServerErrorMiddleware - सुनिश्चित करें कि एप्लिकेशन अपवाद एक कस्टम 500 पृष्ठ वापस कर सकता है या DEBUG मोड में एप्लिकेशन की ट्रेस जानकारी प्रदर्शित कर सकता है। यह हमेशा सबसे बाहरी मिडलवेयर परत है।
  • ExceptionMiddleware - अपवाद हैंडलर जोड़ें ताकि विशिष्ट प्रकार के अपेक्षित अपवाद हैंडलर कार्यों से जुड़े हो सकें। उदाहरण के लिए, एक समापन बिंदु के भीतर उठाएं HTTPException(status_code=404) एक कस्टम 404 पृष्ठ अंततः प्रदान किया जाएगा।

मिडलवेयर का मूल्यांकन ऊपर से नीचे तक किया जाता है, इसलिए हमारे नमूना आवेदन में, निष्पादन प्रवाह इस तरह दिखेगा:

  • मिडलवेयर
    • ServerErrorMiddleware
    • TrustedHostMiddleware
    • HTTPSRedirectMiddleware
    • ExceptionMiddleware
  • रूटिंग
  • समापन बिंदु

निम्नलिखित मिडलवेयर कार्यान्वयन te पैकेज में उपलब्ध हैं:

कोर मिडलवेयर

ब्राउज़रों से क्रॉस-ओरिजिन अनुरोधों की अनुमति देने के लिए आउटगोइंग प्रतिक्रियाओं में उपयुक्त COहेडर जोड़ें।

CORSleकार्यान्वयन द्वारा उपयोग किए जाने वाले डिफ़ॉल्ट पैरामीटर डिफ़ॉल्ट रूप से प्रतिबंधात्मक हैं, इसलिए आपको विशिष्ट स्रोतों, विधियों या हेडर को स्पष्ट रूप से सक्षम करने की आवश्यकता है ताकि ब्राउज़रों को क्रॉस-ओरिजिन संदर्भों में उनका उपयोग करने की अनुमति हो।

te.से आयात
te.leसे मिडलवेयर आयात
CORSlete.le.cसे आयात

मार्ग = ...

मिडलवेयर = [
    मिडलवेयर (CORSMiddleware, allow_origins = ['*'])
]

ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

निम्नलिखित तर्कों का समर्थन किया गया:

  • allow_origins - उन स्रोतों की एक सूची जिन्हें क्रॉस-ओरिजिन अनुरोध करने की अनुमति दी जानी चाहिए। उदाहरण के लिए ['https://example.org', 'https://www.example.org'] आप उपयोग कर सकते हैं ['*'] किसी भी स्रोत की अनुमति देने के लिए।
  • allow_origin_regex - एक नियमित अभिव्यक्ति स्ट्रिंग जो उन स्रोतों से मेल खाती है जिनसे क्रॉस-ओरिजिन अनुरोधों की अनुमति दी जानी चाहिए। उदाहरण के लिए: 'https://.*\.example\.org' ...
  • allow_methods - HTविधियों की एक सूची जिसे क्रॉस-ओरिजिन अनुरोधों के लिए अनुमति दी जानी चाहिए। डिफ़ॉल्ट है ['GET'] आप उपयोग कर सकते हैं ['*'] सभी मानक तरीकों की अनुमति देने के लिए।
  • allow_headers - HTअनुरोध हेडर की एक सूची जिसे क्रॉस-ओरिजिन अनुरोधों के लिए समर्थित किया जाना चाहिए। डिफ़ॉल्ट है [] आप उपयोग कर सकते हैं ['*'] सभी हेडर की अनुमति देने के लिए। COअनुरोधों के लिए, Accept , Accept-Language , Content-Language और Content-Type हेडर को हमेशा अनुमति दी जाती है।
  • allow_credentials - इंगित करता है कि क्रॉस-ओरिजिन अनुरोधों के लिए कुकीज़ का समर्थन किया जाना चाहिए। डिफ़ॉल्ट है False इसके अलावा, क्रेडेंशियल्स की अनुमति देने के लिए, allow_origins , allow_methods और allow_headers पर सेट नहीं किया जा सकता है ['*'] उन सभी को स्पष्ट रूप से निर्दिष्ट किया जाना चाहिए।
  • expose_headers - किसी भी प्रतिक्रिया हेडर को इंगित करता है जो ब्राउज़र के लिए सुलभ होना चाहिए। डिफ़ॉल्ट है [] ...
  • max_age - COप्रतिक्रियाओं को कैश करने के लिए ब्राउज़र के लिए सेकंड में अधिकतम समय सेट करें। डिफ़ॉल्ट है 600 ...

मिडलवेयर दो विशिष्ट प्रकार के HTअनुरोधों का जवाब देता है ...

क्रॉस-ओरिजिन रिसोर्स शेयरिंग (CORS) प्रीचेक रिक्वेस्ट

ये साथ हैं Origin और Access-Control-Request-Method कोई हेडर OPTIONS निवेदन। इस मामले में, मिडलवेयर आने वाले अनुरोध को रोक देगा और उपयुक्त COहेडर के साथ जवाब देगा, साथ ही सूचनात्मक उद्देश्यों के लिए 200 या 400 प्रतिक्रिया भी देगा।

सरल अनुरोध

के साथ कुछ भी Origin इस मामले में, मिडलवेयर हमेशा की तरह अनुरोध पारित करेगा, लेकिन प्रतिक्रिया में उपयुक्त COहेडर शामिल करेगा।

बातचीत मिडलवेयर

हस्ताक्षर कुकीज़ के आधार पर HTसत्र जोड़ें। सत्र जानकारी पठनीय है लेकिन परिवर्तनीय नहीं है।

उपयोग request.session शब्दकोश इंटरफ़ेस सत्र डेटा तक पहुंचता है या संशोधित करता है।

निम्नलिखित तर्कों का समर्थन किया गया:

  • secret_key - एक यादृच्छिक स्ट्रिंग होना चाहिए।
  • session_cookie डिफ़ॉल्ट मान "वार्तालाप" है।
  • max_age - सत्र समाप्ति समय (in seconds). डिफ़ॉल्ट 2 सप्ताह है। यदि सेट किया गया है None कुकी में ब्राउज़र सत्र के समान मान्य अवधि होगी।
  • same_site - eध्वज क्रॉस-साइट अनुरोधों के दौरान ब्राउज़र को सत्र कुकीज़ भेजने से रोकता है। डिफ़ॉल्ट है 'lax' ...
  • path - सत्र कुकी के लिए निर्धारित पथ। डिफ़ॉल्ट है '/' ...
  • https_only - इंगित करता है कि एक सुरक्षा ध्वज सेट किया जाना चाहिए (only HTTके साथ उपयोग के लिए). डिफ़ॉल्ट है False ...
  • domain - कुकी डोमेन का उपयोग सबडोमेन या डोमेन के बीच कुकीज़ साझा करने के लिए किया जाता है। ब्राउज़र डिफ़ॉल्ट रूप से डोमेन को उसी होस्ट पर सेट करते हैं जहां कुकीज़ सेट की जाती हैं, सबडोमेन को छोड़कर (reference).

    te.से आयात te.leसे मिडलवेयर आयात से te.le.सत्र Sleleआयात करते हैं

    मार्ग = ...

    मिडलवेयर = [ मिडलवेयर (सेशनमिडलवेयर, सीक्रेट_की = ..., https://only = True) ]

    ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

HTTमिडलवेयर को पुनर्निर्देशित करता है

जनादेश दें कि सभी आने वाले अनुरोध होने चाहिए https या wss किसी भी आने वाले http या ws अनुरोध को सुरक्षा योजना में पुनर्निर्देशित किया जाएगा।

te.से आयात
te.leसे मिडलवेयर आयात
te.le.htpsreसे आयात HTTPSRedirectMiddleware

मार्ग = ...

मिडलवेयर = [
    मिडलवेयर (HTTPSRedirectMiddleware)
]

ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

इस मिडलवेयर क्लास के लिए कोई कॉन्फ़िगरेशन विकल्प नहीं हैं।

विश्वसनीय मेजबान मिडलवेयर

यह अनिवार्य है कि सभी आने वाले अनुरोधों में सही सेटिंग्स हों Host HTहोस्ट हेडर हमलों से बचाने के लिए हेडर।

te.से आयात
te.leसे मिडलवेयर आयात
te.le.edआयात TrustedHostMiddleware

मार्ग = ...

मिडलवेयर = [
    मिडलवेयर TrustedHostMiddleware अनुमति_होस्ट्स = example.com example.com है'])
]

ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

निम्नलिखित तर्कों का समर्थन किया गया:

  • allowed_hosts - डोमेन की एक सूची जिसे मेजबान के रूप में अनुमति दी जानी चाहिए। जैसे कि *.example.com ऐसे वाइल्ड-कार्ड डोमेन का उपयोग सबडोमेन से मेल खाने के लिए किया जा सकता है। किसी भी होस्टनाम की अनुमति देने के लिए, उपयोग करें allowed_hosts=["*"] या मिडलवेयर को छोड़ दें।
  • www_redirect - यदि सही पर सेट किया गया है, तो अनुमत मेजबानों के गैर-www संस्करणों के अनुरोधों को उनके www समकक्षों पर पुनर्निर्देशित किया जाएगा True ...

यदि आने वाले अनुरोध को ठीक से मान्य नहीं किया जाता है, तो 400 प्रतिक्रिया भेजी जाएगी।

Gp मिडलवेयर

किसी से भी निपटें Accept-Encoding हेडर में शामिल हैं "gzip" अनुरोध पर Gp प्रतिक्रिया।

मिडलवेयर मानक और स्ट्रीमिंग दोनों प्रतिक्रियाओं को संभालेगा।

te.से आयात
te.leसे मिडलवेयर आयात
से te.le.gआयात Gpleआयात


मार्ग = ...

मिडलवेयर = [
    मिडलवेयर (GZipMiddleware, minimul_size = 1000, com= 9)
]

ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

निम्नलिखित तर्कों का समर्थन किया गया:

  • minimum_size - इस न्यूनतम बाइट आकार से छोटे प्रतिक्रियाओं के लिए Gp संपीड़न न करें। डिफ़ॉल्ट है 500 ...
  • compresslevel - Gp संपीड़न के दौरान उपयोग किया जाता है। यह 1 से 9 तक एक पूर्णांक है। डिफ़ॉल्ट मान है 9 मान जितना कम होगा, संपीड़न की गति उतनी ही तेज होगी, लेकिन फ़ाइल का आकार जितना बड़ा होगा; मान जितना अधिक होगा, संपीड़न की गति धीमी होगी, लेकिन फ़ाइल का आकार उतना ही छोटा होगा

मिडलवेयर सेट नहीं किया जाएगा Content-Encoding प्रतिक्रियाएं GZip-compressed हैं ताकि उन्हें दो बार एन्कोड होने से रोका जा सके।

बेसHTमिडलवेयर

एक सार वर्ग जो आपको अनुरोध / प्रतिक्रिया इंटरफ़ेस के लिए ASGI मिडलवेयर लिखने की अनुमति देता है।

उपयोग

उपयोग करने के लिए BaseHTTPMiddleware एक मिडलवेयर क्लास को लागू करने के लिए, आपको ओवरराइड करना होगा async def dispatch(request, call_next) विधि।

te.से आयात
te.leसे मिडलवेयर आयात
से te.le.आयात eHTTPlele


कक्षा CustomHeaderMiddleware (BaseHTTPMiddleware):
    nc def प्रेषण (स्व, अनुरोध, call_next):
        प्रतिक्रिया = कॉल का इंतजार करें _ अगला (अनुरोध)
        प्रतिक्रियाएं। हेडर ['कस्टम'] = 'परीक्षा'
        वापसी प्रतिक्रिया

मार्ग = ...

मिडलवेयर = [
    मिडलवेयर (CustomHeaderMiddleware)
]

ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

यदि आप मिडलवेयर कक्षाओं के लिए कॉन्फ़िगरेशन विकल्प प्रदान करना चाहते हैं, तो आपको ओवरराइड करना चाहिए __init__ यह सुनिश्चित करने की विधि कि पहला तर्क है app , कोई भी शेष पैरामीटर वैकल्पिक कीवर्ड पैरामीटर हैं। यदि आप करते हैं, तो इसे उदाहरण पर सेट करना सुनिश्चित करें app विशेषता।

कक्षा CustomHeaderMiddleware (BaseHTTPMiddleware):
    D__ init__ (स्व, ऐप, हेडर _ मूल्य = 'उदाहरण'):
        सुपर (). __init__ (app)
        f.header_value = header_value

    nc def प्रेषण (स्व, अनुरोध, call_next):
        प्रतिक्रिया = कॉल का इंतजार करें _ अगला (अनुरोध)
        प्रतिक्रिया.ers ['कस्टम'] = self.header_value
        वापसी प्रतिक्रिया


मिडलवेयर = [
    मिडलवेयर CustomHeaderMiddleware हैडर _ मूल्य = 'अनुकूलित')
]

ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

मिडलवेयर कक्षाएं नहीं होनी चाहिए __init__ एक विधि के बाहर इसकी स्थिति को संशोधित करें। इसके बजाय, आपको किसी भी राज्य को अंदर छोड़ देना चाहिए dispatch एक विधि के लिए स्थानीय, या मिडलवेयर उदाहरण की स्थिति को बदलने के बजाय इसे स्पष्ट रूप से पास करें।

सीमा

वर्तमान में, BaseHTTPMiddleware कुछ ज्ञात सीमाएँ हैं:

  • उपयोग BaseHTTPMiddleware को रोकेगा contextlib.ContextVar परिवर्तनों को ऊपर की ओर प्रचारित किया जाता है। यही है, यदि आप हैं ContextVar एक मान सेट करें और इसे रिले से पढ़ने का प्रयास करें, और आप पाएंगे कि मान आपके द्वारा समापन बिंदु में सेट किए गए से अलग है (इस व्यवहार के उदाहरण के लिए यह परीक्षण देखें)।

इन सीमाओं को दूर करने के लिए, शुद्ध ASGI मिडलवेयर का उपयोग करें, जैसा कि नीचे दिखाया गया है।

शुद्ध ASGI मिडलवेयर

ASGI विनिर्देश ASGI इंटरफ़ेस का उपयोग करके सीधे ASGI मिडलवेयर को लागू करना संभव बनाता है, ASGI अनुप्रयोगों की एक श्रृंखला के रूप में, घूमना में अगले एक को कॉल करता है। वास्तव में, यह है कि कैसे tete के साथ भेजे गए मिडलवेयर वर्गों को लागू किया जाता है।

यह निचले स्तर का दृष्टिकोण व्यवहार पर अधिक नियंत्रण प्रदान करता है और फ्रेमवर्क और सर्वर में अंतर को बढ़ाता है BaseHTTPMiddleware की सीमाएं।

शुद्ध ASGI मिडलवेयर लिखना

ASGI मिडलवेयर बनाने का सबसे आम तरीका एक वर्ग का उपयोग करना है।

कक्षा ASGIIleware:
    डेफ __ इनिट__ (self, app):
        self.app = ऐप

    nc def __ कॉल __ (स्व, गुंजाइश, प्राप्त, भेजें):
        self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)

उपरोक्त मिडलवेयर सबसे बुनियादी ASGI मिडलवेयर है। यह अपने कंस्ट्रक्टर में पैरामीटर के रूप में एक माता-पिता ASGI एप्लिकेशन लेता है और एक को लागू करता है async __call__ विधि जो मूल एप्लिकेशन को आमंत्रित करती है।

कुछ कार्यान्वयन, जैसे किasgi-cors, फ़ंक्शन का उपयोग करके एक वैकल्पिक शैली का उपयोग करते हैं:

आयात उपकरण

Dasgi _ मिडलवेयर ():
    Dasgi_decorator (app):

        @functools.wraps (ऐप)
        nc def लपेटा_ऐप (गुंजाइश, प्राप्त, भेजें):
            प्रतीक्षा करें ऐप (गुंजाइश, प्राप्त, भेजें)

        लिपटे _ ऐप पर लौटें

    वापसी asgi _ डेकोरेटर

हालांकि, ASGI मिडलवेयर एक कॉल करने योग्य वस्तु होनी चाहिए जो तीन मापदंडों को स्वीकार करती है:scope,receive, और send।

  • scope एक शब्दकोश है जो कनेक्शन के बारे में जानकारी रखता है scope["type"] हो सकता है:
    • "http" : HTअनुरोधों के लिए उपयोग किया जाता है।
    • "websocket" : कनेक्शन के लिए उपयोग किया जाता है।
    • "lifespan" : ASGI जीवनचक्र संदेशों के लिए।
  • receive और send ASGI सर्वर के साथ ASGI ईवेंट संदेशों का आदान-प्रदान करने के लिए उपयोग किया जा सकता है - नीचे इस पर अधिक। इन संदेशों का प्रकार और सामग्री गुंजाइश प्रकार पर निर्भर करती है। ASGI विनिर्देश में अधिक जानें।

शुद्ध ASGI मिडलवेयर का उपयोग करना

शुद्ध ASGI मिडलवेयर का उपयोग किसी भी अन्य मिडलवेयर की तरह ही किया जा सकता है।

te.से आयात
te.leसे मिडलवेयर आयात

मिडलवेयर से ASGIleआयात करें

मार्ग = ...

मिडलवेयर = [
    मिडलवेयर (ASGIMiddleware),
]

ऐप = स्टारलेट (..., middleware=middleware)

मिडलवेयर का उपयोग करना भी देखें।

एनोटेशन टाइप करें

मिडलवेयर में टिप्पणियों को जोड़ने के दो तरीके हैं: स्वयं का उपयोग करना या asgiref ...

  • का उपयोग करना: सबसे आम उपयोग के मामलों के लिए उपयुक्त है।

    से te.आयात ASGIIApp, संदेश, स्कोप, प्राप्त, भेजें

    कक्षा ASGIIleware: डेफ __ इनिट__ (self, app: ASGIApp) - > कोई नहीं: self.app = ऐप

    Ac def __ call__ (सेल्फ, स्कोप: स्कोप, रिसीव: रिसीव, सेंड: सेंड) -> कोई नहीं:
        यदि गुंजाइश ["प्रकार"]! = "http":
            वापसी self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)
    
        Ac def send_wrapper (message: Message) - > कोई नहीं:
            # ... कुछ करो
            भेजने का इंतजार (संदेश)
    
        self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, send_rapper)
    
  • asgiref का उपयोग करता है: सख्त प्रकार के संकेत प्राप्त करने के लिए।

    asgi.आयात से ASGI3Application, ASGIEceCallable, ASGISendCallable, स्कोप asgi.आयात ASGIEceveEvent, ASGISendसे

    कक्षा ASGIIleware: D__init__ (स्व, ऐप: ASGI3Application) -> कोई नहीं: self.app = ऐप

    Ac def __ call__ (स्व, गुंजाइश: स्कोप, प्राप्त: ASGIEceCallable, भेजें: ASGISendCallable) -> कोई नहीं:
        यदि गुंजाइश ["प्रकार"]! = "http":
            self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)
            वापसी
    
        Ac def send_wrapper (संदेश: ASGISendEvent) -> कोई नहीं:
            # ... कुछ करो
            भेजने का इंतजार (संदेश)
    
        वापसी self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, send_rapper)
    

सामान्य पैटर्न

केवल कुछ अनुरोधों को संभालें

ASGI मिडलवेयर हो सकता है scope सामग्री विशिष्ट व्यवहारों को लागू करती है।

उदाहरण के लिए, केवल HTअनुरोधों को संभालने के लिए, लिखें ...

कक्षा ASGIIleware:
    डेफ __ इनिट__ (self, app):
        self.app = ऐप

    nc def __ कॉल __ (स्व, गुंजाइश, प्राप्त, भेजें):
        यदि गुंजाइश ["प्रकार"]! = "http":
            self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)
            वापसी

        # यहाँ कुछ करो!

        self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)

इसी तरह, केवल वेबसॉकेट मिडलवेयर scope["type"] != "websocket" पर संरक्षित है।

मिडलवेयर अनुरोध विधि, URL, हेडर और इसी तरह के आधार पर अलग तरह से व्यवहार कर सकता है।

मल्टीप्लेक्सिंग स्टारलेट घटक

te कई डेटा संरचनाएं प्रदान करता है जो ASGI को स्वीकार करते हैं। scope , receive और/या send पैरामीटर जो आपको अमूर्त के उच्च स्तर पर काम करने में सक्षम बनाते हैं। ऐसी डेटा संरचनाओं में शामिल हैं Request , Headers , QueryParams , URL रुकिए।

उदाहरण के लिए, आप तुरंत कर सकते हैं Request HTअनुरोधों को अधिक आसानी से जांचने के लिए:

स्टारलेट से। अनुरोध आयात अनुरोध

कक्षा ASGIIleware:
    डेफ __ इनिट__ (self, app):
        self.app = ऐप

    nc def __ कॉल __ (स्व, गुंजाइश, प्राप्त, भेजें):
        यदि गुंजाइश ["प्रकार"] == "http":
            अनुरोध = अनुरोध (गुंजाइश)
            ... #`request.method`,`request.url`,`request.headers`, आदि का उपयोग करें।

        self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)

आप प्रतिक्रियाओं का पुन: उपयोग भी कर सकते हैं, जो ASGI एप्लिकेशन भी हैं।

एक उत्सुक प्रतिक्रिया भेजें

कनेक्शन की जाँच करें scope आपको सशर्त रूप से विभिन्न ASGI अनुप्रयोगों को कॉल करने की अनुमति देता है। एक उपयोग मामला एप्लिकेशन को कॉल किए बिना प्रतिक्रिया भेजने का हो सकता है।

उदाहरण के लिए, यह मिडलवेयर अनुरोधित पथ के आधार पर एक स्थायी पुनर्निर्देशित करने के लिए एक शब्दकोश का उपयोग करता है। यदि आपको रूटिंग पैटर्न को रिफ्लेक्टर करने की आवश्यकता है, तो इसका उपयोग विरासत URL के लिए चल रहे समर्थन को लागू करने के लिए किया जा सकता है।

te.aसे आयात किया गया
rette.से आयात किया गया

कक्षा पुनर्निर्देशमिडलवेयर:
    D__ init__ (स्व, ऐप, path_mapping: dict):
        self.app = ऐप
        सेल्फ.पैथ_मैपिंग = पैथ_मैपिंग

    nc def __ कॉल __ (स्व, गुंजाइश, प्राप्त, भेजें):
        यदि गुंजाइश ["प्रकार"]! = "http":
            self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)
            वापसी

        = (scope = scope)

        यदि url.in स्व। path_maping:
            url = url.(path=self.path_maping [url.path])
            प्रतिक्रिया = पुनर्निर्देशन (url, status_code = 301)
            प्रतिक्रिया की प्रतीक्षा (गुंजाइश, प्राप्त, भेजें)
            वापसी

        self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)

उदाहरण उपयोग इस तरह दिखेगा:

te.से आयात
te.leसे मिडलवेयर आयात

मार्ग = ...

पुनर्निर्देशन = {
    "/ v1 / संसाधन /": "/ v2 / संसाधन /",
    # ...
}

मिडलवेयर = [
    मिडलवेयर mapping=redirections
]

ऐप = स्टारलेट (मार्ग = मार्ग, middleware=middleware

अनुरोध की जाँच करें या संशोधित करें

अनुरोध जानकारी द्वारा संचालित किया जा सकता है scope एक्सेस या बदलने के लिए। इस पैटर्न के पूर्ण उदाहरण के लिए, Uका देखें ProxyHeadersMiddleware यह फ्रंट-एंड प्रॉक्सी के पीछे सेवाएं प्रदान करते समय जांच और समायोजन करता है scope ...

इसके अलावा, पैकेजिंग receive ASGI कॉल करने योग्य वस्तुएं आपको हेरफेर करने में सक्षम बनाती हैं http.request HTअनुरोध निकाय तक पहुंचने या संशोधित करने के लिए ASGI इवेंट संदेश।

उदाहरण के लिए, यह मिडलवेयर आने वाले अनुरोध निकाय के आकार की गणना और रिकॉर्ड करता है ...

कक्षा LoggedRequestBodySizeMiddleware
    डेफ __ इनिट__ (self, app):
        self.app = ऐप

    nc def __ कॉल __ (स्व, गुंजाइश, प्राप्त, भेजें):
        यदि गुंजाइश ["प्रकार"]! = "http":
            self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)
            वापसी

        शरीर _ आकार = 0

        Ac def प्राप्त _ लॉगिंग _ अनुरोध _ शरीर _ आकार ():
            नॉनलोकल बॉडी_साइज़

            संदेश = प्रतीक्षा प्राप्त करें ()
            संदेश ["प्रकार"] == "htp.request"

            शरीर _ आकार + = लेन (message.get) ("body", b "))

            यदि संदेश नहीं है। ("more_body, "गलत):
                प्रिंट (च) "अनुरोध निकाय का आकार था: {body_size} बाइट्स ")

            वापसी संदेश

        प्रतीक्षा self.app (गुंजाइश, प्राप्त _ लॉगिंग _ अनुरोध _ शरीर _ आकार, भेजें)

इसी तरह, मिडलवेयर संचालित हो सकता है websocket.receive आने वाले डेटा की जांच करने या बदलने के लिए ASGI इवेंट संदेश।

HTअनुरोध निकाय को बदलने के उदाहरण के लिए, देखें msgpack-asgi ...

प्रतिक्रिया की जाँच करें या संशोधित करें

होगा send ASGI कॉल करने योग्य रैपर जो आपको अंतर्निहित एप्लिकेशन द्वारा भेजे गए HTप्रतिक्रिया का निरीक्षण या संशोधन करने की अनुमति देते हैं। इसे प्राप्त करने के लिए, कृपया http.response.start या http.response.body ASGI इवेंट संदेशों पर प्रतिक्रिया दें।

उदाहरण के लिए, यह मिडलवेयर कुछ निश्चित अतिरिक्त प्रतिक्रिया हेडर जोड़ता है:

tableers te.aसे आयात करते हैं

कक्षा ExtraResponseHeadersMiddleware
    डेफ __ इनिट__ (self, app, headers):
        self.app = ऐप
        f.ers = हेडर

    nc def __ कॉल __ (स्व, गुंजाइश, प्राप्त, भेजें):
        यदि गुंजाइश ["प्रकार"]! = "http":
            वापसी self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)

        Ac def send_with_extract_headers (message):
            यदि संदेश ["प्रकार"] == "htp.response.start":
                हेडर = म्यूटेबलहेडर (scope = message)
                कुंजी के लिए, स्वयं में मान:
                    हेडर्स.पेंड (key, value)

            भेजने का इंतजार (संदेश)

        self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, send_with_extract_headers)

यह भी देखें asgi-logger HTप्रतिक्रियाओं की जाँच करने और कॉन्फ़िगरेशन योग्य HTएक्सेस लॉग लाइनों को लॉग करने का एक उदाहरण है।

इसी तरह, मिडलवेयर संचालित हो सकता है websocket.send आउटगोइंग डेटा की जांच करने या बदलने के लिए ASGI इवेंट संदेश।

कृपया ध्यान दें कि यदि आप प्रतिक्रिया निकाय बदलते हैं, तो आपको प्रतिक्रिया अपडेट करने की आवश्यकता होगी Content-Length नई प्रतिक्रिया शरीर की लंबाई से मेल खाने के लिए हेडर। एक पूर्ण उदाहरण के लिए, देखें brotli-asgi ...

समापन बिंदु पर जानकारी पास करें

यदि आपको अंतर्निहित एप्लिकेशन या समापन बिंदु के साथ जानकारी साझा करने की आवश्यकता है, तो आप इसे स्टोर कर सकते हैं scope शब्दकोश में। ध्यान दें कि यह एक सम्मेलन है - उदाहरण के लिए, te एंडपॉइंट के साथ रूटिंग जानकारी साझा करने के लिए इस विधि का उपयोग करता है - लेकिन यह ASGI विनिर्देश का हिस्सा नहीं है। यदि आप करते हैं, तो उन कुंजियों का उपयोग करना सुनिश्चित करें जो संघर्षों से बचने के लिए अन्य मिडलवेयर या अनुप्रयोगों द्वारा उपयोग किए जाने की संभावना नहीं है।

उदाहरण के लिए, जब निम्नलिखित मिडलवेयर शामिल होता है, तो समापन बिंदु इसे एक्सेस करने में सक्षम होगा request.scope["asgi_transaction_id"] ...

आयात करें id

कक्षा TransactionIDMiddleware
    डेफ __ इनिट__ (self, app):
        self.app = ऐप

    nc def __ कॉल __ (स्व, गुंजाइश, प्राप्त, भेजें):
        स्कोप ["asgi_traction_id"] = id.id4 ()
        self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)

सफाई और त्रुटि हैंडलिंग

आप एक पैकेज में एप्लिकेशन को पैकेज कर सकते हैं try/except/finally सफाई संचालन करने या त्रुटि हैंडलिंग करने के लिए एक ब्लॉक या संदर्भ प्रबंधक में।

उदाहरण के लिए, निम्नलिखित मिडलवेयर मैट्रिक्स एकत्र कर सकते हैं और एप्लिकेशन अपवादों को संभाल सकते हैं ...

आयात समय

कक्षा MonitoringMiddleware
    डेफ __ इनिट__ (self, app):
        self.app = ऐप

    nc def __ कॉल __ (स्व, गुंजाइश, प्राप्त, भेजें):
        प्रारंभ = समय ()
        कोशिश:
            self.app प्रतीक्षा करें (गुंजाइश, प्राप्त, भेजें)
        अपवाद को छोड़कर exc:
            ... # अपवाद की प्रक्रिया करें
            उठाएँ
        अंत में:
            अंत = समय ()
            समाप्त = अंत - प्रारंभ
            ... # सबमिट करें `elapsed` एक निगरानी बैकएंड के लिए एक मीट्रिक के रूप में

यह भी देखें timing-asgi इस पैटर्न का एक पूरा उदाहरण प्राप्त करने के लिए।

संभावित समस्याएं

ASGI मिडलवेयर स्टेटलेस होना चाहिए

चूंकि ASGI को समवर्ती अनुरोधों को संभालने के लिए डिज़ाइन किया गया है, इसलिए किसी भी कनेक्शन-विशिष्ट स्थिति को सीमित किया जाना चाहिए __call__ कार्यान्वयन के दायरे में। ऐसा करने में विफलता के परिणामस्वरूप आमतौर पर अनुरोधों में चर पढ़ने / लिखने के टकराव होते हैं, और त्रुटियां होने की संभावना होती है।

उदाहरण के लिए, यदि कोई प्रतिक्रिया है X-Mock हेडर, यह संक्रिया सशर्त रूप से प्रतिक्रिया निकाय को बदल देगा ...

✅ करना

```python
from starlette.datastructures import Headers

class MockResponseBodyMiddleware:
    def __init__(self, app, content):
        self.app = app
        self.content = content

    async def __call__(self, scope, receive, send):
        if scope["type"] != "http":
            await self.app(scope, receive, send)
            return

        # A flag that we will turn `True` if the HTTP response
        # has the 'X-Mock' header.
        # ✅: Scoped to this function.
        should_mock = False

        async def maybe_send_with_mock_content(message):
            nonlocal should_mock

            if message["type"] == "http.response.start":
                headers = Headers(raw=message["headers"])
                should_mock = headers.get("X-Mock") == "1"
                await send(message)

            elif message["type"] == "http.response.body":
                if should_mock:
                    message = {"type": "http.response.body", "body": self.content}
                await send(message)

        await self.app(scope, receive, maybe_send_with_mock_content)
```

❌ नहीं।

```python hl_lines="7-8"
from starlette.datastructures import Headers

class MockResponseBodyMiddleware:
    def __init__(self, app, content):
        self.app = app
        self.content = content
        # ❌: This variable would be read and written across requests!
        self.should_mock = False

    async def __call__(self, scope, receive, send):
        if scope["type"] != "http":
            await self.app(scope, receive, send)
            return

        async def maybe_send_with_mock_content(message):
            if message["type"] == "http.response.start":
                headers = Headers(raw=message["headers"])
                self.should_mock = headers.get("X-Mock") == "1"
                await send(message)

            elif message["type"] == "http.response.body":
                if self.should_mock:
                    message = {"type": "http.response.body", "body": self.content}
                await send(message)

        await self.app(scope, receive, maybe_send_with_mock_content)
```

यह भी देखें GZipMiddleware एक पूर्ण नमूना कार्यान्वयन प्राप्त करने के लिए जो इस संभावित मुद्दे को संबोधित करता है।

आगे पढ़ना

यह दस्तावेज़ ASGI मिडलवेयर बनाने के लिए एक अच्छी नींव के रूप में पर्याप्त होना चाहिए।

हालांकि, इस विषय पर कई उत्कृष्ट लेख हैं:

अन्य रूपरेखाओं में मिडलवेयर का उपयोग करना

अन्य ASGI अनुप्रयोगों के आसपास ASGI मिडलवेयर लपेटने के लिए, आपको एप्लिकेशन उदाहरणों को लपेटने के लिए अधिक सामान्य पैटर्न का उपयोग करना चाहिए:

ऐप = TrustedHostMiddleware (ऐप, अनुमति_होस्ट्स = example.com

आप इसे एक te एप्लिकेशन उदाहरण के साथ भी कर सकते हैं, लेकिन इसका उपयोग करना बेहतर है middleware=<List of Middleware instances> शैली, क्योंकि यह होगा:

  • सुनिश्चित करें कि सब कुछ एक बाहरी परत में लिपटा हुआ है ServerErrorMiddleware में।
  • शीर्ष रखें app उदाहरण।

रूटिंग समूहों के लिए मिडलवेयर लागू करना

मिडलवेयर को भी जोड़ा जा सकता है Mount एक उदाहरण में, यह आपको रूटिंग या सबएप्लिकेशन के एक सेट पर मिडलवेयर लागू करने की अनुमति देता है:

te.से आयात
te.leसे मिडलवेयर आयात
से te.le.gआयात Gpleआयात
स्टारलेट से। रूटिंग आयात माउंट, रूट


मार्ग = [
    माउंट (
        "/",
        मार्ग = [
            मार्ग (
                "/ उदाहरण",
                समापन बिंदु = ...,
            )
        ],
        मिडलवेयर = [मिडलवेयर (GZipMiddleware)]
    )
]

ऐप = स्टारलेट (routes = routes)

कृपया ध्यान दें कि इस तरीके से उपयोग किया जाने वाला मिडलवेयर उतना उपयोगी नहीं है जितना कि यह है Starlette एप्लिकेशन का मिडलवेयर अपवाद हैंडलिंग मिडलवेयर में लिपटा हुआ है। यह आमतौर पर एक समस्या नहीं है क्योंकि यह केवल जाँच या संशोधित करने के लिए उपयुक्त है Response फिर भी, आप शायद इस तर्क को त्रुटि प्रतिक्रियाओं पर लागू नहीं करना चाहते हैं। यदि आप केवल कुछ मार्गों पर त्रुटि प्रतिक्रियाओं के लिए मिडलवेयर तर्क लागू करना चाहते हैं, तो कुछ विकल्प हैं:

  • मौजूद है Mount ऊपर एक जोड़ें ExceptionMiddleware
  • अपने मिडलवेयर में एक जोड़ें try/except ब्लॉक करें, और वहां से एक त्रुटि प्रतिक्रिया लौटाएं
  • मार्कअप और प्रसंस्करण को दो मिडलवेयर में विभाजित करें, एक में रखा गया है Mount पर, प्रतिक्रिया को प्रसंस्करण की आवश्यकता के रूप में चिह्नित करें (जैसे सेटिंग द्वारा) scope["log-response"] = True ), एक और आवेदन Starlette भारी उठाने को पूरा करने के लिए आवेदन।

Route / WebSocket कक्षा भी एक को स्वीकार करती है middleware पैरामीटर जो आपको एकल मार्ग पर मिडलवेयर लागू करने की अनुमति देते हैं:

te.से आयात
te.leसे मिडलवेयर आयात
से te.le.gआयात Gpleआयात
स्टारलेट से। रूटिंग आयात मार्ग


मार्ग = [
    मार्ग (
        "/ उदाहरण",
        समापन बिंदु = ...,
        मिडलवेयर = [मिडलवेयर (GZipMiddleware)]
    )
]

ऐप = स्टारलेट (routes = routes)

आप मिडलवेयर को भी लागू कर सकते हैं Router कक्षा, जो आपको मार्गों के एक सेट पर मिडलवेयर लागू करने की अनुमति देती है।

te.से आयात
te.leसे मिडलवेयर आयात
से te.le.gआयात Gpleआयात
स्टारलेट से। रूटिंग आयात रूट, राउटर


मार्ग = [
    मार्ग ("/ उदाहरण", समापन बिंदु = ...),
    मार्ग ("/ अन्य", समापन बिंदु = ...),
]

राउटर = राउटर (मार्ग = मार्ग, मिडलवेयर = [मिडलवेयर (GZipMiddleware)])

तीसरे पक्ष के मिडलवेयर

असगी-औथ-गिथुब

यह मिडलवेयर किसी भी ASGI एप्लिकेशन में प्रमाणीकरण जोड़ता है, जिससे उपयोगकर्ताओं को अपने Hub खाते के साथ लॉग इन करने की आवश्यकता होती है (via OAuth). एक्सेस को विशिष्ट उपयोगकर्ताओं या किसी विशिष्ट Hub संगठन या टीम के सदस्यों तक सीमित किया जा सकता है।

agi-csrf

CSहमलों से बचाने के लिए मिडलवेयर। यह मिडलवेयर एक डबल-कमिट कुकी मोड को लागू करता है, जहां एक कुकी सेट की जाती है और फिर फॉर्म फ़ील्ड को छिपाने के लिए csrfके साथ जोड़ा जाता है या x-csrftoken तुलना के लिए HTहेडर।

ऑथलिब मिडलवेयर

ऑथलिब के JWT मॉड्यूल का उपयोग करते हुए, te के सत्र मिडलवेयर का एक सीधा विकल्प।

बुग्सनैग मिडलवेयर

Bugके अपवादों को लॉग करने के लिए एक मिडलवेयर वर्ग।

CSमिडलवेयर

CSहमलों से बचाने के लिए मिडलवेयर। यह मिडलवेयर एक डबल-कमिट कुकी मोड को लागू करता है जिसमें एक कुकी सेट की जाती है और फिर एक के साथ जोड़ा जाता है x-csrftoken तुलना के लिए HTहेडर।

प्रारंभिक डेटा मिडलवेयर

पहले TL1.3 डेटा अनुरोधों का पता लगाने और अस्वीकार करने के लिए मिडलवेयर और डेकोरेटर।

प्रोमेथियस मिडलवेयर

चल रहे अनुरोधों, समय, आदि सहित अनुरोधों और प्रतिक्रियाओं से संबंधित प्रोमेथियस मैट्रिक्स को कैप्चर करने के लिए एक मिडलवेयर वर्ग ...

प्रॉक्सी हेडर मिडलवेयर

Uमें एक मिडलवेयर क्लास होता है जिसका उपयोग प्रॉक्सी सर्वर का उपयोग करते समय किया जा सकता है X-Forwarded-Proto और X-Forwarded-For हेडर क्लाइंट साइड पता निर्धारित करता है। अधिक जटिल प्रॉक्सी कॉन्फ़िगरेशन के लिए, आपको इस मिडलवेयर को समायोजित करने की आवश्यकता हो सकती है।

मिडलवेयर को सीमित करने वाली दर

मिडलवेयर को सीमित करने वाली दर। नियमित अभिव्यक्ति मिलान URL; लचीले नियम; अत्यधिक अनुकूलन। उपयोग करने में बहुत आसान।

अनुरोध मिडलवेयर

अनुरोध ID पढ़ने/उत्पन्न करने और उन्हें एप्लिकेशन लॉग में संलग्न करने के लिए एक मिडलवेयर वर्ग।

रोलबार मिडलवेयर

रोलबार में अपवाद, त्रुटियों और लॉग संदेशों को लॉग करने के लिए एक मिडलवेयर वर्ग।

StarletteOpentracing

एक मिडलवेयर क्लास जो OpenTracing.io ट्रैकर्स को ट्रैकिंग जानकारी भेजता है और इसका उपयोग वितरित अनुप्रयोगों का विश्लेषण और निगरानी करने के लिए किया जा सकता है।

सुरक्षा कुकी मिडलवेयर

अनुकूलन योग्य मिडलवेयर जोड़ने के लिए स्वचालित कुकी एन्क्रिप्शन और डिक्रिप्शन अनुप्रयोगों के लिए, मौजूदा कुकी-आधारित मिडलवेयर के लिए अतिरिक्त समर्थन प्रदान करता है।

टाइमिंग मिडलवेयर

एक मिडलवेयर वर्ग जो प्रत्येक अनुरोध के लिए समय की जानकारी (सीपीयू समय और दीवार घड़ी समय) का उत्सर्जन करता है जो इससे गुजरता है। इन टाइमिंग को स्टैटस मेट्रिक्स के रूप में कैसे उत्सर्जित किया जाए, इसका एक उदाहरण शामिल है।

WSGIleवेयर

WSGI अनुप्रयोगों को ASGI अनुप्रयोगों में परिवर्तित करने के लिए जिम्मेदार एक मिडलवेयर वर्ग।