Django a un ProxyModel. Comment est-ce pratique à utiliser et quand est-ce utile?
Modèle proxy https://docs.djangoproject.com/en/3.0/topics/db/models/#proxy-models
Ceci n'est que l'explication.
Vous souhaiterez peut-être modifier uniquement le comportement de Python dans votre modèle. Nous pouvons changer le gestionnaire par défaut ou ajouter de nouvelles méthodes.
Cependant, il semble qu'il existe différents points de démangeaisons et je me demande comment l'utiliser de manière pratique. C'est juste un moyen utile, donc je ne veux pas le forcer. Right way to return proxy model instance from a base model instance in Django?
Django est une structure qui vous permet d'avoir plusieurs applications dans votre projet. Un modèle courant est de créer un écran d'administration avec Django (un outil d'administration pour les personnes à l'intérieur au lieu de Django Admin) et une API avec DRF? Dans de tels moments, vous souhaiterez souvent utiliser la base de données en commun pour ces deux applications. Par exemple, un service à grande échelle est converti en un micro-service, et il peut ne pas être divisé (géré) de cette manière, mais je pense qu'il existe de nombreuses configurations de ce type dans les startups qui veulent avant tout des résultats.
Lors de la prise d'une telle configuration, il est nécessaire d'utiliser un modèle commun dans Django et DRF, mais cela peut être trouvé assez facilement en recherchant, et le système est terminé et implémenté pratiquement rien. Il n'y a pas de problème.
L'ORM de Django est excellent et j'ai rarement l'occasion d'écrire du SQL brut, mais je ne pense pas que ce soit correct d'écrire des instructions ORM en vue. C'est comme ça.
class MyViewSet(mixins.ListModelMixin, viewsets.GenericViewSet):
queryset = schema.MyObject.objects.all().order_by('id')
serializer_class = MyObjectSerializer
Quelle est la différence entre ceci et l'ancien "Ne pas écrire SQL dans Controller"? Savez-vous que ce n'est pas bon si vous faites comme ça?
class MyViewSet(mixins.ListModelMixin, viewsets.GenericViewSet):
queryset = schema.MyObject.objects.filter(type=schema.MyObject.TYPE.OPEN).order_by('id')
serializer_class = MyObjectSerializer
Donc, je pense qu'il vaut mieux écrire une méthode en modèle.
class MyViewSet(mixins.ListModelMixin, viewsets.GenericViewSet):
queryset = schema.MyObject.filter_of_open_object()
serializer_class = MyObjectSerializer
class MyObject(models.Model):
@classmethod
def filter_of_open_object(cls):
return cls..objects.filter(type=schema.MyObject.TYPE.OPEN).order_by('id')
Comme ça.
Dans l'exemple, la requête de type LIST qui répertorie même les données supprimées logiquement requises pour l'application d'administration n'est pas requise du côté API. Si vous le frappez par erreur plutôt que inutile (c'est une erreur d'implémentation), vous vous retrouverez avec des données que vous ne devriez pas afficher.
__ ProxyModel peut être utilisé dans de tels cas. __
C'est comme ça.
Exemple d'écriture de ProxyModel
class Article(XModel):
TYPE = Choices(
('DRAFT', 'Brouillon'),
('PUBLISH', 'Ouvert'),
)
type = StatusField(
choices_name='TYPE',
blank=False,
default=TYPE.DRAFT,
help_text="Statut de l'article",
)
text = models.TextField(
null=False,
blank=False,
default="",
help_text="Contenu de l'article",
)
writer = models.ForeignKey(
to="Account",
related_name="articles",
null=False,
on_delete=models.DO_NOTHING,
help_text="Rédacteur d'article",
)
class ArticleProxy(ProxyModel, schema.Article):
@classmethod
def list_of_draft(cls):
return cls.objects.filter(type=cls.TYPE.DRAFT)
Veuillez écrire dans ce formulaire. Le point est cls.objects.filter
. Même si la signification est la même, s'il s'agit de schema.Article.objects.filter
, la valeur de retour sera un tableau de ʻArticle` (à proprement parler, il s'agit d'un QuerySet, pas d'un tableau).
class ArticleProxy(ProxyModel, schema.Article):
@classmethod
def list_of_future(cls):
return cls.objects.filter(resavation_at=now())
class MyViewSet(mixins.ListModelMixin, viewsets.GenericViewSet):
queryset = ArticleProxy.list_of_future()
serializer_class = ArticleSerializer
Savez-vous que c'est un bug? now () n'est évalué qu'une seule fois et n'est pas calculé à chaque fois qu'il y a une demande. L'essence de ce problème est que les méthodes (ou fonctions à l'ancienne) sont essentiellement des boîtes noires et doivent être appelées sans connaître leur contenu. Dans cet exemple, l'implémenteur de View dit généralement "__ Il existe une méthode pratique, utilisons-la! __".
Il y a une idée (en moi) que même la communication est inutile dans les startups qui démarrent des entreprises à une vitesse explosive. Je sens que c'est une époque où 1on1 est recommandé et où la gestion est mise en avant en passant de l'épinard au zassou, mais chez XTech, les organisations qui ont besoin de gestion sont anciennes, chacune n'est pas professionnelle, c'est donc le cas. Je pense que j'ai besoin. (La partie la plus longue de ma carrière est la gestion, mais w)
Bref, je pense qu'un framework qui peut être compris sans communication même lors de sa mise en œuvre, et que si vous le faites normalement, vous ne créerez pas d'étranges bugs ou failles de sécurité est important pour augmenter la productivité.
La personne qui implémente chaque application ajoute une méthode sur ProxyModel et l'utilise. Vous ne pouvez pas accéder aux données auxquelles seul l'administrateur peut accéder si vous l'utilisez normalement (sauf si vous écrivez une telle méthode)
Il existe également une solution de contournement dans le cas où vous écrivez une méthode dans le modèle donné dans l'exemple ci-dessus et elle est utilisée comme une boîte noire pour résoudre un bogue. Je me demande si vous pouvez l'imaginer ou le mettre dans le prochain contenu.
Puisqu'il s'agit d'un gribouillage, je pense qu'il y a des erreurs typographiques et des parties étranges, donc si vous pouvez commenter, je prendrai le temps de le revoir!
Recommended Posts