Kem Intensif Pembangunan Bahagian Belakang FastAPI · Pelajaran

Parameter Penapisan dan Pengisihan Dinamik

Bina model parameter pertanyaan boleh guna semula untuk penapisan, pengisihan dan pemilihan medan dengan pengesahan.

Pelajaran 3 daripada 413 langkah

Parameter Penapisan dan Pengisihan Dinamik ialah pelajaran Kem Intensif Pembangunan Bahagian Belakang FastAPI percuma di CoddyKit. Ini ialah pelajaran 3 daripada 4. Sebanyak 3 pelajaran dalam laluan pembelajaran ini boleh dibaca sepenuhnya secara percuma — selepas itu, CoddyKit PRO membuka akses kepada semua pelajaran, serta latihan praktikal dengan penyunting kod terbina dalam dan tutor kecerdasan buatan yang tersedia 24/7. Pelajaran ini merupakan sebahagian daripada laluan pembelajaran Kem Intensif Pembangunan Bahagian Belakang FastAPI, dan kemajuan anda disegerakkan merentas web serta aplikasi CoddyKit. Kursus Kem Intensif Pembangunan Bahagian Belakang FastAPI merangkumi sejumlah 4 pelajaran.

Mengapa Parameter Pertanyaan Dinamik?

Titik akhir senarai dunia sebenar jarang memulangkan segala-galanya. Klien mahu menapis (hanya pengguna aktif), mengisih (yang terbaharu dahulu), dan memilih medan (hanya id dan nama). Menetapkan setiap gabungan secara keras akan menyebabkan bilangan laluan bertambah secara melampau.

Pendekatan yang kemas ialah memodelkan parameter pertanyaan ini sebagai objek boleh guna semula yang telah disahkan, kemudian memasukkannya ke dalam banyak titik akhir. Dalam pelajaran ini, kita membina:

  • Model penapis yang menukar parameter pertanyaan kepada kekangan selamat
  • Penghurai isihan dengan senarai benarkan medan dan arah
  • Mekanisme pemilihan medan untuk mengecilkan muatan respons

Segala-galanya dipacu oleh kebergantungan FastAPI supaya kekal DRY dan mudah diuji.

Mengumpulkan Penapis dengan Kelas Kebergantungan

Kelas dengan __init__ yang menerima parameter Query menjadi kebergantungan yang boleh digunakan semula. FastAPI membaca setiap parameter daripada URL dan mendokumenkannya dalam OpenAPI secara automatik.

Gunakan Optional[...] = None supaya penapis bersifat pilihan: parameter yang tiada bermaksud "jangan tapis lajur ini".

from typing import Optional
from fastapi import Query

class UserFilterParams:
    def __init__(
        self,
        status: Optional[str] = Query(None, description="active | inactive"),
        min_age: Optional[int] = Query(None, ge=0, le=150),
        search: Optional[str] = Query(None, min_length=2, max_length=50),
    ):
        self.status = status
        self.min_age = min_age
        self.search = search

# Usage:
# @app.get('/users')
# def list_users(filters: UserFilterParams = Depends()):
#     ...

Mengesahkan Nilai Penapis dengan Enum

Penapis teks bebas seperti status=foo membenarkan input yang tidak sah. Hadkannya dengan Enum berasaskan str: FastAPI menolak apa-apa yang berada di luar set yang dibenarkan dan memaparkan menu juntai bawah dalam dokumentasi.

Ini ialah barisan pertahanan pertama — nilai penapis yang tidak sah menghasilkan 422 yang kemas, bukannya meresap ke lapisan pertanyaan anda.

from enum import Enum
from typing import Optional
from fastapi import Query

class UserStatus(str, Enum):
    active = "active"
    inactive = "inactive"
    pending = "pending"

class UserFilterParams:
    def __init__(
        self,
        status: Optional[UserStatus] = Query(None),
        min_age: Optional[int] = Query(None, ge=0, le=150),
    ):
        self.status = status
        self.min_age = min_age

Menukar Penapis kepada Predikat

Asingkan lapisan HTTP daripada lapisan data. Kebergantungan hanya mengumpul dan mengesahkan; pembantu kecil menukar objek yang telah diisi kepada predikat penapis sebenar.

Berikut ialah versi tanpa rangka kerja yang boleh anda jalankan, dengan penapis digunakan pada kamus biasa. Corak yang sama boleh dipetakan dengan kemas kepada panggilan SQLAlchemy .filter() kemudian.

USERS = [
    {"id": 1, "name": "Ada", "status": "active", "age": 36},
    {"id": 2, "name": "Linus", "status": "inactive", "age": 54},
    {"id": 3, "name": "Grace", "status": "active", "age": 41},
]

def apply_filters(rows, status=None, min_age=None, search=None):
    result = rows
    if status is not None:
        result = [r for r in result if r["status"] == status]
    if min_age is not None:
        result = [r for r in result if r["age"] >= min_age]
    if search is not None:
        result = [r for r in result if search.lower() in r["name"].lower()]
    return result

print(apply_filters(USERS, status="active", min_age=40))

Menghuraikan Parameter Isihan

Kontrak biasa ialah ?sort=-created_at,name: senarai dipisahkan koma yang tanda - pada awalnya bermaksud menurun. Huraikannya menjadi tuple (field, direction).

Jangan sekali-kali mempercayai nama medan daripada klien. Sahkan setiap medan terhadap senarai benarkan supaya pengguna tidak boleh mengisih mengikut atau menyiasat lajur sewenang-wenangnya.

ALLOWED_SORT = {"created_at", "name", "age", "id"}

def parse_sort(sort_param):
    parsed = []
    for token in sort_param.split(","):
        token = token.strip()
        if not token:
            continue
        descending = token.startswith("-")
        field = token[1:] if descending else token
        if field not in ALLOWED_SORT:
            raise ValueError(f"Cannot sort by '{field}'")
        parsed.append((field, "desc" if descending else "asc"))
    return parsed

print(parse_sort("-created_at,name"))
print(parse_sort("age"))

Kebergantungan Isihan Boleh Guna Semula

Bungkus penghurai dalam kebergantungan supaya setiap titik akhir senarai berkongsi kontrak dan pengesahan isihan yang sama. Menaikkan HTTPException(422) untuk medan yang tidak sah memberikan ralat yang tepat dan boleh dibaca mesin kepada klien.

Dengan menghantar senarai benarkan, kebergantungan ini boleh digunakan semula merentas sumber yang mempunyai lajur boleh isih yang berbeza.

from typing import Optional
from fastapi import Query, HTTPException

def sort_dependency(allowed: set):
    def _parse(sort: Optional[str] = Query(None, example="-created_at,name")):
        if not sort:
            return []
        parsed = []
        for token in sort.split(","):
            token = token.strip()
            if not token:
                continue
            desc = token.startswith("-")
            field = token[1:] if desc else token
            if field not in allowed:
                raise HTTPException(422, f"Invalid sort field: {field}")
            parsed.append((field, "desc" if desc else "asc"))
        return parsed
    return _parse

# @app.get('/users')
# def list_users(sort=Depends(sort_dependency({'created_at','name'}))):
#     ...

Menggunakan Isihan Berbilang Kunci dalam Memori

Berbilang kunci isihan mesti digunakan mengikut susunan. Kaedah stabilnya ialah mengisih mengikut kunci paling kurang penting dahulu dan bergerak ke belakang, kerana sorted Python adalah stabil.

Contoh kendiri ini mencerminkan hasil yang akan diberikan oleh pangkalan data dengan ORDER BY a, b DESC.

ROWS = [
    {"name": "Ada", "age": 36},
    {"name": "Grace", "age": 36},
    {"name": "Linus", "age": 54},
]

def apply_sort(rows, sort_keys):
    result = list(rows)
    for field, direction in reversed(sort_keys):
        result.sort(key=lambda r: r[field], reverse=(direction == "desc"))
    return result

ordered = apply_sort(ROWS, [("age", "desc"), ("name", "asc")])
for r in ordered:
    print(r)

Pemilihan Medan (Set Medan Jarang)

Untuk mengecilkan muatan, sokong ?fields=id,name. Klien memilih kunci yang ingin dipulangkan. Seperti biasa, sahkan pilihan terhadap senarai benarkan medan yang boleh didedahkan supaya lajur dalaman (seperti password_hash) tidak boleh diminta sama sekali.

Pemilihan ialah langkah unjuran yang digunakan selepas penapisan dan pengisihan, sejurus sebelum pensirilan.

EXPOSABLE = {"id", "name", "status", "age"}

def select_fields(rows, fields_param):
    if not fields_param:
        return rows
    requested = {f.strip() for f in fields_param.split(",") if f.strip()}
    invalid = requested - EXPOSABLE
    if invalid:
        raise ValueError(f"Unknown fields: {sorted(invalid)}")
    return [{k: r[k] for k in requested if k in r} for r in rows]

data = [{"id": 1, "name": "Ada", "status": "active", "age": 36}]
print(select_fields(data, "id,name"))

Menggabungkan Penapis, Isihan, Pemilihan dan Paginasi

Susunan saluran paip penting untuk ketepatan dan kecekapan: tapis dahulu untuk mengurangkan set, kemudian isih, selepas itu bahagikan kepada halaman (hiris), dan akhirnya pilih medan pada halaman yang dipulangkan.

Memilih medan sebelum paginasi masih akan mengimbas segala-galanya, manakala melakukan paginasi sebelum pengisihan akan memulangkan halaman yang salah.

def list_resource(rows, *, filters, sort_keys, fields, offset, limit,
                  apply_filters, apply_sort, select_fields):
    rows = apply_filters(rows, **filters)
    rows = apply_sort(rows, sort_keys)
    total = len(rows)
    page = rows[offset: offset + limit]
    page = select_fields(page, fields)
    return {"total": total, "items": page,
            "offset": offset, "limit": limit}

# In FastAPI each piece is a Depends(); the route just calls list_resource.

Menggubah Kebergantungan menjadi Satu Objek Pertanyaan

Daripada menghantar empat kebergantungan berasingan ke setiap laluan, gubahkannya. Kebergantungan pembungkus boleh memulangkan satu objek kemas yang mengandungi penapis, kunci isihan, medan dan paginasi.

Ini memastikan tandatangan laluan pendek dan memberikan anda satu tempat untuk mengembangkan kontrak pertanyaan.

from dataclasses import dataclass
from typing import Optional
from fastapi import Depends, Query

@dataclass
class ListQuery:
    filters: object
    sort: list
    fields: Optional[str]
    offset: int
    limit: int

def list_query(
    filters: "UserFilterParams" = Depends(),
    sort: list = Depends(sort_dependency({"created_at", "name"})),
    fields: Optional[str] = Query(None),
    offset: int = Query(0, ge=0),
    limit: int = Query(20, ge=1, le=100),
) -> ListQuery:
    return ListQuery(filters, sort, fields, offset, limit)

# @app.get('/users')
# def list_users(q: ListQuery = Depends(list_query)):
#     ...

Mendokumenkan dan Menetapkan Lalai Kontrak

Kontrak pertanyaan yang baik adalah mendokumentasikan dirinya sendiri dan selamat secara lalai:

  • Berikan setiap Query description dan example supaya dokumentasi OpenAPI menerangkan sintaksnya.
  • Hadkan limit dengan le=100 supaya klien tidak boleh meminta sejuta baris.
  • Pilih pengisihan lalai yang munasabah (contohnya yang paling baharu dahulu) supaya hasil kekal deterministik merentas halaman.
  • Tolak medan/kunci pengisihan yang tidak diketahui dengan 422 dan bukannya mengabaikannya secara senyap.

Tertib deterministik amat penting: tanpa pengisihan yang stabil, penomboran halaman boleh mengulangi atau melangkau baris antara permintaan.

Semakan Pantas: Urutan Saluran

Anda mendedahkan GET /products yang menyokong penapisan, pengisihan, penomboran halaman dan set medan jarang. Dalam urutan apakah operasi ini harus digunakan untuk mengembalikan halaman yang betul dengan cekap?

Ringkasan

Anda membina lapisan pertanyaan boleh guna semula yang disahkan untuk titik akhir senarai FastAPI:

  • Penapis sebagai kelas kebergantungan dengan parameter Optional serta pengesahan Enum/kekangan.
  • Pengisihan yang dihuraikan daripada sintaks -field,field terhadap senarai benarkan, dan menghasilkan 422 untuk medan yang tidak diketahui.
  • Pemilihan medan (set medan jarang) yang dihadkan kepada senarai benarkan yang boleh didedahkan bagi melindungi lajur dalaman.
  • Kebergantungan ListQuery yang digabungkan untuk memastikan tandatangan laluan kekal kemas.

Ingat salurannya: tapis → isih → nomborkan halaman → pilih, sentiasa dengan pengisihan lalai yang deterministik supaya penomboran halaman kekal konsisten. Corak ini boleh dipetakan terus kepada pertanyaan SQLAlchemy apabila anda beralih daripada data dalam ingatan kepada pangkalan data sebenar.

Percuma untuk bermula

Pelajari Kem Intensif Pembangunan Bahagian Belakang FastAPI dengan tutor kecerdasan buatan — percuma

Tulis dan jalankan kod sebenar dalam pelayar anda, dapatkan bantuan segera daripada tutor kecerdasan buatan yang tersedia 24/7, dan sambung semula dari tempat anda berhenti di web atau dalam aplikasi.

Kursus
21
Pelajaran
84

Soalan Lazim

Adakah pelajaran “Parameter Penapisan dan Pengisihan Dinamik” percuma?

Ya — sebanyak 3 pelajaran dalam laluan pembelajaran Kem Intensif Pembangunan Bahagian Belakang FastAPI, termasuk “Parameter Penapisan dan Pengisihan Dinamik”, boleh dibaca sepenuhnya secara percuma di web ini. Selepas itu, CoddyKit PRO membuka akses kepada semua pelajaran, serta latihan interaktif dengan penyunting kod terbina dalam dan tutor kecerdasan buatan yang tersedia 24/7. Kursus Kem Intensif Pembangunan Bahagian Belakang FastAPI merangkumi sejumlah 4 pelajaran.

Apakah yang akan saya pelajari dalam “Parameter Penapisan dan Pengisihan Dinamik”?

Bina model parameter pertanyaan boleh guna semula untuk penapisan, pengisihan dan pemilihan medan dengan pengesahan. Anda berlatih Kem Intensif Pembangunan Bahagian Belakang FastAPI menggunakan kod praktikal yang dijalankan terus dalam pelayar, manakala tutor kecerdasan buatan 24/7 menjawab soalan anda semasa anda mengikuti pelajaran.

Adakah saya memerlukan pengalaman untuk memulakan Kem Intensif Pembangunan Bahagian Belakang FastAPI?

Tiada pengalaman terdahulu diperlukan. Pembelajaran Kem Intensif Pembangunan Bahagian Belakang FastAPI di CoddyKit disusun untuk pelajar daripada peringkat pemula hingga lanjutan, jadi anda boleh bermula di sini atau dari awal dan belajar mengikut kadar anda sendiri. Ini ialah pelajaran 3 daripada 4.

Berapa lamakah pelajaran “Parameter Penapisan dan Pengisihan Dinamik” diambil?

Kebanyakan pelajaran CoddyKit mengambil masa kira-kira 5–10 minit. Setiap pelajaran ringkas dan interaktif, jadi anda boleh membuat kemajuan secara berterusan dan menyambung tepat dari tempat anda berhenti di web atau aplikasi.

Bolehkah saya menulis dan menjalankan kod dalam pelajaran Kem Intensif Pembangunan Bahagian Belakang FastAPI ini?

Ya. Setiap pelajaran Kem Intensif Pembangunan Bahagian Belakang FastAPI menyertakan penyunting kod terbina dalam, jadi anda boleh menulis dan menjalankan kod sebenar terus dalam pelayar serta menerima maklum balas kecerdasan buatan serta-merta — tanpa memerlukan persediaan setempat.

Semua pelajaran dalam kursus ini

  1. Perversian URL, Pengepala dan Jenis Media
  2. Penomboran Kursor berbanding Ofset pada Skala Besar
  3. Parameter Penapisan dan Pengisihan Dinamik
  4. Mereka Bentuk Sampul Tindak Balas yang Stabil
← Kembali ke Kem Intensif Pembangunan Bahagian Belakang FastAPI