[PYTHON] FastAPI Tutorial Memo Teil 2 Pfadparameter

Einführung

FastAPI Souce: https://github.com/tiangolo/fastapi FastAPI Document: https://fastapi.tiangolo.com

Ziel: Pfadparameter (https://fastapi.tiangolo.com/tutorial/path-params/)

Hinweise zum FastAPI-Tutorial.

Dies ist eine Fortsetzung von FastAPI Tutorial Note 1. Die FastAPI-Installation und der Serverstart sind die gleichen wie oben. Lesen Sie daher den obigen Artikel.

Grundsätzlich beziehe ich mich auf das offizielle Tutorial von Fast API, aber ich lasse einige Teile weg oder ändere die Reihenfolge für mein eigenes Lernen. Die korrekten und detaillierten Informationen finden Sie in der offiziellen Dokumentation.

Da ich ein Anfänger von Web & Python bin und mich bei der Übersetzung auf Google und DeepL verlasse, würde ich mich freuen, wenn Sie auf Fehler hinweisen könnten.

Entwicklungsumgebung

Ubuntu 20.04 LTS Python 3.8.2 pipenv 2018.11.26

Ziel

Verfahren

Intro

Mit FastAPI können Sie Parameter und Variablen für Pfade in derselben Syntax wie das Python-Format deklarieren. Speichern Sie den folgenden Code als main.py.

main.py


from fastapi import FastAPI

app = FastAPI()


@app.get("/items/{item_id}")
async def read_item(item_id):
    return {"item_id": item_id}

Zu diesem Zeitpunkt ist die item_id der Dekorationsfunktion@app.get (" / items / {item_id} ") der ** Pfadparameter **, der als Argument item_id an das Funktionsargument übergeben wird. Starten Sie beispielsweise nach dem Speichern dieser Datei den Server (uvicorn main: app --reload) und öffnen Sie http://127.0.0.1:8000/items/foo in Ihrem Browser. Sie sollten einen JSON-formatierten Text mit der Zeichenfolge foo erhalten, die der Variablen item_id zugewiesen ist, wie unten gezeigt.

{"item_id":"foo"}

Aktueller Bildschirm

qiita_2_1 2020-07-12 22-53-23.png

Dies ist die Basis des Parameters ** Path ** in der Fast API.

Typisierter Pfadparameter

Mit FastAPI können Sie den Typ des ** Pfadparameters ** in einer Funktion mithilfe von Standardanmerkungen vom Typ Python deklarieren.

main


~
#Unterlassung
~

@app.get("/items/{item_id}")
async def read_item(item_id: int):
    return {"item_id": item_id}

Beachten Sie die Zeile "async def read_item (item_id: int):", die die Funktion deklariert. Hier wird das Argument item_id als int (Integer-Typ) deklariert. Typdeklarationen bieten Ihnen Editorunterstützung wie Fehlerprüfung und Wortvervollständigung. (Wenn ich im obigen Code Zahlen und Zeichenfolgen wie "foo = item_id +" bar "" hinzufüge, wird in meiner Umgebung (PyCharm) ein Fehler von Type Checker angezeigt.)

Wenn Sie http://127.0.0.1:8000/items/3 mit dem obigen Code öffnen und den Funktionsteil von main.py geändert haben, wird Folgendes angezeigt.

{"item_id":3}

Hierbei ist zu beachten, dass der von der Funktion "read_item" empfangene und als Rückgabewert angezeigte Wert keine Zeichenfolge, sondern eine Ganzzahl "3" ist. Standardmäßig werden alle Eingaben in die URL als Zeichenfolge interpretiert, aber die Typdeklaration von Python analysiert die Anforderung automatisch (analysiert) und konvertiert sie in einen ganzzahligen Typ.

Http://127.0.0.1 mit dem Code (async def read_item (item_id: int): Teil wird ohne den Teil, der den Typ deklariert, zurück in async def read_item (item_id):) geändert Wenn Sie auf Folgendes zugreifen: 8000 / items / 3, wird es als Zeichenfolge "3" angezeigt.

{"item_id":"3"}

Wenn Sie mit einer URL wie http://127.0.0.1:8000/items/foo auf den als "int" -Typ deklarierten Path-Parameter zugreifen, wird der folgende HTTP-Fehler zurückgegeben.

{
    "detail": [
        {
            "loc": [
                "path",
                "item_id"
            ],
            "msg": "value is not a valid integer",
            "type": "type_error.integer"
        }
    ]
}

Dies liegt daran, dass die Funktion ** Datenvalidierung ** von FastAPI funktioniert hat, weil der angegebene Parameter (str Typ" foo ") nicht in den Typ int konvertiert werden konnte. Ähnlich wie beim obigen Typ "str" erhalten Sie einen ähnlichen Fehler, wenn Sie einen Float-Typ "Floating Minority Point" (z. B. http://127.0.0.1:8000/items/4.2) angeben.

Außerdem wurde bestätigt, dass ein Wert vom Typ "int", der einem mit dem Typ "float" deklarierten Parameter zugewiesen wird, konvertiert wird.

Aus dem Obigen können wir ersehen, dass die Fast-API genau dieselbe Validierung wie die Python-Typdeklaration durchführt.

Beachten Sie, dass die Fehlermeldung auch den Punkt angibt, an dem die Validierung nicht bestanden wurde (in diesem Fall die Parametervariable "path" "item_id"). Es ist sehr nützlich, um Code zu entwickeln und zu debuggen, der mit der API interagiert.

Das Verhindern von Fehlern bei der Typprüfung ist eine der Hauptfunktionen der Fast API.

Überprüfen Sie das Dokument

Überprüfen Sie nach dem Überprüfen des obigen Codes http://127.0.0.1:8000/docs in Ihrem Browser. Die interaktive API-Dokumentation wird automatisch generiert (siehe unten). (Klicken Sie auf die blaue Registerkarte "GET" unter "default" in der Mitte des Bildschirms, um sie zu erweitern.)

qiita_2_2 2020-07-13 19-25-40.png

Es gibt eine Ganzzahl unter dem Namen "item_id" von "Parameters". Sie können sehen, dass die Python-Typdeklaration auch in der interaktiven Dokumentation (in die Swagger-Benutzeroberfläche integriert) enthalten ist. Dieses Dokument enthält viele Informationen zur API und kann mit Designern und Mitarbeitern vor Ort geteilt werden.

Dieses Dokument basiert ebenfalls auf dem von FastAPI generierten Schema, das generierte Schema ist jedoch OpenAPI-kompatibel und es wurden verschiedene kompatible Tools entwickelt. Wie ich in Memo 1 bestätigt habe, gibt es ein alternatives Dokument, das ReDoc in Fast API verwendet. Versuchen Sie, http://127.0.0.1:8000/redoc zu besuchen.

qiita_2_3 2020-07-13 19-40-37.png

Es ist ein grober persönlicher Eindruck, aber Swagger UI ist ein interaktives Dokument, das tatsächlich eine Anfrage generieren und das Ergebnis überprüfen kann, während ReDoc ein statisches und einfaches Dokument ist. Vielleicht gibt es mehr Möglichkeiten, es und andere Tools zu verwenden, aber ich bin mir aufgrund mangelnder Studien überhaupt nicht sicher. Es tut mir Leid. Ich möchte es aktualisieren, sobald ich es lerne.

Im Moment halte ich die Swagger-Benutzeroberfläche für praktisch, mit der Anfragen generiert und die Ergebnisse angezeigt werden können.

Pydantic Zurück zum Hauptthema: Alle Typanmerkungen, die für eine solche Dokumentgenerierung nützlich sind, werden von einer Bibliothek namens ** Pydantic ** erstellt. Der folgende Artikel war hilfreich für Pydantic. Einführung in Pydantic @ 0622okakyo

** Pydantic ** ermöglicht es, dass viele Datentypen wie "str", "float", "bool" auf die gleiche Weise mit Anmerkungen versehen werden.

Bestellproblem im Pfadbetrieb

Beim Erstellen einer Pfadoperation kann der Pfad festgelegt werden.

Angenommen, Sie haben einen Pfad namens "/ users / me", über den Benutzer ihre eigenen Daten abrufen können. Nehmen wir zu diesem Zeitpunkt an, dass es auch einen Pfad namens "/ users / {user_id}" gibt, der gleichzeitig mit "user_id" Daten über einen anderen Benutzer abruft.

Die Pfadoperation in FastAPI wird der Reihe nach ausgewertet. Daher muss der Pfad "/ users / me" vor dem Pfad "/ users / {user_id}" deklariert werden, wie unten gezeigt.

main


from fastapi import FastAPI

app = FastAPI()


@app.get("/users/me")
async def read_user_me():
    return {"user_id": "the current user"}


@app.get("/users/{user_id}")
async def read_user(user_id: str):
    return {"user_id": user_id}

Wenn der Pfad / users / me nach dem Pfad / users / {user_id} wie unten gezeigt deklariert wird, wird der Wert me als Parameter user_id an die Fast API übergeben.

main_miss


from fastapi import FastAPI

app = FastAPI()


@app.get("/users/{user_id}")  # <- "/users/me"Wenn Sie die GET-Methode erhalten können"me"Ist bestanden
async def read_user(user_id: str):
    return {"user_id": user_id}


@app.get("/users/me")   # <- "/users/me"Diese Funktion wird nicht aufgerufen, da sie bereits ausgewertet wurde
async def read_user_me():
    return {"user_id": "the current user"}

Vordefinierte Werte

Wenn Sie einen Pfadoperator haben, der Pfadparameter akzeptiert und gültige Werte für diese Parameter vordefinieren möchten, empfehlen wir die Verwendung des Standard-Python-Moduls "Enum".

Zuerst erstellen wir die Klasse "Enum".

Importieren Sie "Enum" und erstellen Sie eine Unterklasse, die "str" und "Enum" erbt. Durch das Erben von "str" kann das API-Dokument im Voraus wissen, dass der festzulegende Wert ein Zeichenfolgentyp ist und korrekt gerendert wird.

Erstellen Sie als Nächstes ein Klassenattribut mit einem festen Wert, der ein gültiger Wert ist.

main


from enum import Enum   # <-Enum importieren

from fastapi import FastAPI


class ModelName(str, Enum): # <-Klassenvererbung
    alexnet = "alexnet"     # <-Klassenattribute(Fester Wert)Schaffung
    resnet = "resnet"
    lenet = "lenet"


app = FastAPI()

Wir werden die Pfadparameter anhand der definierten Klasse definieren.

Verwenden Sie die von Ihnen erstellte Aufzählungstypklasse (ModelName), um einen Pfadparameter mit Typanmerkungen zu erstellen.

main


from enum import Enum

from fastapi import FastAPI


class ModelName(str, Enum):
    alexnet = "alexnet"
    resnet = "resnet"
    lenet = "lenet"


app = FastAPI()


@app.get("/model/{model_name}")
async def get_model(model_name: ModelName): # <-Pfadparameter mit Typanmerkung
    if model_name == ModelName.alexnet:
        return {"model_name": model_name, "message": "Deep Learning FTW!"}

    if model_name.value == "lenet":
        return {"model_name": model_name, "message": "LeCNN all the images"}

    return {"model_name": model_name, "message": "Have some residuals"}

Überprüfen Sie die Dokumentation (http://127.0.0.1:8000/docs). Die für Pfadparameter verfügbaren Werte sind vordefiniert, sodass das Dokument diese Werte interaktiv anzeigt und auswählt.

  1. Klicken Sie auf die Registerkarte "GET" und dann oben auf der Registerkarte auf "Try it out".
  2. model_name wird auswählbar.
  3. Sie können eine Anfrage senden, indem Sie einen Wert auswählen und auf "Execte" klicken.

(Der folgende Screenshot stammt aus dem offiziellen Dokument (https://fastapi.tiangolo.com/tutorial/path-params/). Ich konnte keinen guten Screenshot des Auswahlbildschirms in meiner Umgebung erhalten. )

qiita_2_4 2020-07-13 23-00-54.png

Informationen zum Aufzählungstyp

main


from enum import Enum

from fastapi import FastAPI


class ModelName(str, Enum):
    alexnet = "alexnet"
    resnet = "resnet"
    lenet = "lenet"


app = FastAPI()


@app.get("/model/{model_name}")
async def get_model(model_name: ModelName):
    if model_name == ModelName.alexnet: # <- ①
        return {"model_name": model_name, "message": "Deep Learning FTW!"}  # <- ③

    if model_name.value == "lenet": # <- ②
        return {"model_name": model_name, "message": "LeCNN all the images"}    # <- ③ 

    return {"model_name": model_name, "message": "Have some residuals"}     # <- ③ 

Weitere Informationen finden Sie unter Python-Dokument enum --- Unterstützung für Aufzählungstypen.

Vergleichen Sie hier den erstellten ModelName mit dem Aufzählungstypelement (①), ermitteln Sie den Aufzählungstypwert mit .value und vergleichen Sie ihn (②) und verwenden Sie das Aufzählungstypelement als Rückgabewert (③). Ich bin. Selbst im Fall eines verschachtelten JSON-Körpers wie dem Wörterbuchtyp "dict" ist es möglich, den Wert von Path Operater als Aufzählungselement zurückzugeben. In diesem Fall wird es in den entsprechenden Wert (oben "str") konvertiert und an den Client zurückgegeben.

Wenn Sie es in einem interaktiven Dokument oder Browser erhalten, erhalten Sie beispielsweise den folgenden JSON-Rückgabewert.

{
  "model_name": "alexnet",
  "message": "Deep Learning FTW!"
}

Pfadparameter einschließlich Pfad

Angenommen, Sie haben eine Pfadoperation mit dem Pfad "/ files / {file_path}". Aber wenn file_path selbst einen Pfad als Wert hat (wie file_path = home / johndoe / myfile.txt) Die URL würde folgendermaßen aussehen:

http://127.0.0.1:8000/files/home/johndoe/myfile.txt

OpenAPI unterstützt die Deklaration von Pfadparametern mit dem obigen Pfad als Wert nicht, da dies zur Definition von Tests und zum Auftreten schwieriger Szenarien führt.

Mithilfe der internen Tools von Starlette können Sie mit der Fast API solche Pfadparameter deklarieren. (Es kann jedoch nicht bestätigt werden, dass der Pfadparameter selbst den Pfad im API-Dokument enthält, der OpenAPI entspricht. * Das Dokument selbst funktioniert.)

Deklarieren Sie Pfadparameter, einschließlich Pfade, unter Verwendung einer URL, die der folgenden ähnelt:

/files/{file_path:path}

Oben ist der Pfadparameter "Dateipfad", und der Teil ": Pfad" gibt an, dass der Pfadparameter den Pfad enthält.

Das Verwendungsbeispiel lautet wie folgt.

main


from fastapi import FastAPI

app = FastAPI()


@app.get("/files/{file_path:path}")
async def read_file(file_path: str):
    return {"file_path": file_path}

Am Ende

Das nächste Mal wird es ein Abfrageparameter sein.

Recommended Posts

FastAPI Tutorial Memo Teil 2 Pfadparameter
FastAPI Tutorial Memo Teil 3 Abfrageparameter
FastAPI Tutorial Memo Teil 1
Django Tutorial Memo
Python OpenCV Tutorial Memo
FastAPI Tutorial Memo Teil 1
Hinweise zum Pyramiden-Tutorial (single_file_tasks)
FastAPI Tutorial Memo Teil 3 Abfrageparameter
FastAPI Tutorial Memo Teil 2 Pfadparameter
Django Tutorial Memo
[Für Memo] Linux Teil 2
Listen Sie das Schreiben von Memos Teil 2 auf
Python-Grundnotiz - Teil 2
Python OpenCV Tutorial Memo
Python-Grundnotiz - Teil 1
Android HCE Survey Memo (Teil 2)
Linux Standard Lehrbuch Memo 1 Teil 2
Python-Grammatik-Grundnotiz (1)
Linux Standard Lehrbuch Memo Teil 6