Problème
Comme recommandé dans l'article de blog Best Practices for Designing a Pragmatic RESTful API , je voudrais ajouter un fields
paramètre de requête à une API basée sur Django Rest Framework qui permet à l'utilisateur de sélectionner uniquement un sous-ensemble de champs par ressource.
Exemple
Sérialiseur:
class IdentitySerializer(serializers.HyperlinkedModelSerializer):
class Meta:
model = models.Identity
fields = ('id', 'url', 'type', 'data')
Une requête régulière renverrait tous les champs.
GET /identities/
[
{
"id": 1,
"url": "http://localhost:8000/api/identities/1/",
"type": 5,
"data": "John Doe"
},
...
]
Une requête avec le fields
paramètre ne doit renvoyer qu'un sous-ensemble des champs:
GET /identities/?fields=id,data
[
{
"id": 1,
"data": "John Doe"
},
...
]
Une requête avec des champs non valides doit ignorer les champs non valides ou générer une erreur client.
Objectif
Est-ce possible d'une manière ou d'une autre? Sinon, quelle est la manière la plus simple de mettre en œuvre cela? Existe-t-il déjà un package tiers qui le fait déjà?
la source
QUERY_PARAMS
pourquery_params
les versions récentes de Django, mais à part cela, cela fonctionne comme un charme.requests
existe en tant que membre decontext
. Alors que c'est le cas en production, ce n'est pas le cas lors de l'exécution de tests unitaires qui créent les objets manuellement.Cette fonctionnalité est disponible à partir d'un package tiers .
Déclarez votre sérialiseur comme ceci:
Ensuite, les champs peuvent maintenant être spécifiés (côté client) en utilisant des arguments de requête:
Le filtrage d'exclusion est également possible, par exemple pour renvoyer tous les champs sauf id:
avertissement: je suis l'auteur / le mainteneur.
la source
dbrgn
implémentation a quelques différences: 1. ne prend pas en charge exclure avecfields!=key1,key2
. 2. modifie également les sérialiseurs en dehors du contexte de requête GET, ce qui peut interrompre et interrompra certaines requêtes PUT / POST. 3. n'accumule pas les champs avec par exemplefields=key1&fields=key2
, ce qui est un bon choix pour les applications ajax. Il a également une couverture de test nulle, ce qui est quelque peu inhabituel dans OSS.serializers.py
views.py
la source
Configurer une nouvelle classe de sérialiseur de pagination
Créer un sérialiseur dynamique
Enfin, utilisez un mixin de homemage pour vos APIViews
Demande
Désormais, lorsque vous demandez une ressource, vous pouvez ajouter un paramètre
fields
pour afficher uniquement les champs spécifiés dans l'url./?fields=field1,field2
Vous pouvez trouver un rappel ici: https://gist.github.com/Kmaschta/e28cf21fb3f0b90c597a
la source
Vous pouvez essayer Dynamic REST , qui prend en charge les champs dynamiques (inclusion, exclusion), les objets incorporés / chargés latéralement, le filtrage, le classement, la pagination, etc.
la source
Nous avons fourni une telle fonctionnalité dans drf_tweaks / control-over-serialized-fields .
Si vous utilisez nos sérialiseurs, il vous suffit de passer le
?fields=x,y,z
paramètre dans la requête.la source
Pour les données imbriquées, j'utilise Django Rest Framework avec le package recommandé dans la documentation , drf-flexfields
Cela vous permet de restreindre les champs renvoyés sur les objets parent et enfant. Les instructions dans le readme sont bonnes, juste quelques points à surveiller:
L'URL semble avoir besoin du / comme ceci '/ person /? Expand = country & fields = id, name, country' au lieu de comme écrit dans le readme '/ person? Expand = country & fields = id, name, country'
La dénomination de l'objet imbriqué et son nom associé doivent être complètement cohérents, ce qui n'est pas obligatoire autrement.
Si vous avez «plusieurs», par exemple un pays peut avoir plusieurs états, vous devrez définir «plusieurs»: True dans le sérialiseur comme décrit dans la documentation.
la source
Si vous voulez quelque chose de flexible comme GraphQL, vous pouvez utiliser django-restql . Il prend en charge les données imbriquées (à la fois plates et itérables).
Exemple
Une requête régulière renvoie tous les champs.
GET /users
Une requête avec le
query
paramètre en revanche ne renvoie qu'un sous-ensemble des champs:GET /users/?query={id, username}
Avec django-restql, vous pouvez accéder aux champs imbriqués de n'importe quel niveau. Par exemple
GET /users/?query={id, username, date_joined{year}}
Pour les champs imbriqués itérables, par exemple les groupes sur les utilisateurs.
GET /users/?query={id, username, groups{id, name}}
la source