Data Models & IA
Utiliser l’IA pour concevoir, documenter et sécuriser les modèles Django : normalisation, PII, qualité des données, embeddings, migrations & index.
Django ORM · pgvector · Validators · Admin ROI: élevé (réduction bugs & dette) Effort: moyen Complexité: moyenne
Architecture de référence
Modèles Django ←→ (Lint/Doctor IA) ←→ Suggestions (index, uniques, types, PII) → Génération contrôlée (diff/migration) → Tests/CI → Admin (badges PII & qualité) → Option: champs d’embedding + signaux pour MAJ vectorielle
Quick Wins
Pièges & Anti-patterns
Rappels pragmatiques + squelette prêt à l’emploi.
models.py — exemple e-commerce compact python
from django.db import models
class Product(models.Model):
sku = models.CharField(max_length=40, unique=True)
name = models.CharField(max_length=200)
price = models.DecimalField(max_digits=10, decimal_places=2)
class Meta:
indexes = [models.Index(fields=['name'])]
class Order(models.Model):
user = models.ForeignKey('auth.User', on_delete=models.PROTECT)
created_at = models.DateTimeField(auto_now_add=True)
class Meta:
indexes = [models.Index(fields=['user','created_at'])]
constraints = [models.CheckConstraint(check=models.Q(created_at__isnull=False), name='order_ts_not_null')]
class OrderItem(models.Model):
order = models.ForeignKey(Order, on_delete=models.CASCADE, related_name='items')
product = models.ForeignKey(Product, on_delete=models.PROTECT)
qty = models.PositiveIntegerField(default=1)
class Meta:
unique_together = [('order','product')]KPIs à suivre
- Taux de requêtes ‘Full Scan’ → doit baisser
- Nb d’anomalies CheckConstraint / 1k enregistrements
- Latence p95 requêtes clés après indexation
Déclarer les PII au niveau modèle et les rendre visibles dans l’admin.
models.py — annotation PII python
class Customer(models.Model):
email = models.EmailField(unique=True)
phone = models.CharField(max_length=20, blank=True)
date_of_birth = models.DateField(null=True, blank=True)
PII = {'email':'contact', 'phone':'contact', 'date_of_birth':'personal'}admin.py — mixin avec badges & blocage export python
from django.contrib import admin
from django.utils.html import format_html
class PIIAdminMixin:
pii_icon = '<span class="badge bg-danger ms-2">PII</span>'
def get_list_display(self, request):
base = super().get_list_display(request)
return base + ('_pii',)
def _pii(self, obj):
return format_html(self.pii_icon) if getattr(obj.__class__, 'PII', None) else ''
def scrub(val:str)->str:
if not val: return val
return val[:2] + '***' + val[-2:]KPIs à suivre
- % champs PII correctement annotés
- Nb d’exports bloqués/corrigés
- Incidents liés à la fuite PII (=0)
Ajouter un champ vectoriel et le maintenir à jour lorsqu’un texte change.
models.py — champ vectoriel + signal python
from pgvector.django import VectorField
from django.db.models.signals import post_save
from django.dispatch import receiver
class Article(models.Model):
title = models.CharField(max_length=200)
body = models.TextField()
embedding = VectorField(dimensions=1536, null=True)
@receiver(post_save, sender=Article)
def update_embedding(sender, instance, **kwargs):
text = (instance.title or '') + '\n' + (instance.body or '')
# emb = openai_embed(text) # à implémenter
emb = [0.0]*1536
if emb:
type(instance).objects.filter(pk=instance.pk).update(embedding=emb)SQL — index vectoriel sql
CREATE INDEX IF NOT EXISTS article_embedding_ivf
ON article USING ivfflat (embedding vector_cosine_ops) WITH (lists=100);KPIs à suivre
- Couverture embedding (% non-null)
- Latence kNN p95
- Taux de clic sur résultats sémantiques
Un ‘doctor’ qui scanne les modèles et propose des corrections (indexes, uniques, validators).
management command — model_doctor python
from django.core.management.base import BaseCommand
from django.apps import apps
from django.db import models
class Command(BaseCommand):
help = 'Audit des modèles et suggestions (indexes, uniques, types, FK).'
def handle(self, *args, **opts):
for model in apps.get_models():
fields = {f.name: f for f in model._meta.get_fields() if isinstance(f, models.Field)}
if 'email' in fields and not fields['email'].unique:
self.stdout.write(f'[SUGGEST] {model.__name__}.email → unique=True')
for f in fields.values():
if isinstance(f, models.FloatField) and 'price' in f.name:
self.stdout.write(f'[SUGGEST] {model.__name__}.{f.name} → DecimalField')KPIs à suivre
- Nb de suggestions appliquées / sprint
- Réduction d’erreurs d’intégrité
- Score de couverture des bonnes pratiques
L’IA propose; l’humain valide. Générer un ‘diff’ explicite et des migrations idempotentes.
ex. migration d’index composite python
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = []
operations = [
migrations.AddIndex(
model_name='order',
index=models.Index(fields=['user','created_at'], name='order_user_ts'),
)
]KPIs à suivre
- Durée moyenne migration en prod
- Nb de rollback/s
- Latence clés post-déploiement
Prochaines étapes : Brancher un vrai service d’embeddings, intégrer le ‘model_doctor’ à la CI, et afficher un rapport de qualité des modèles dans l’admin.
