Existe-t-il un moyen de créer et d'utiliser dynamiquement des modèles dans Phoenix? J'ai une application qui stocke des métadonnées sur les tables des clients: ils définissent une poignée de champs (noms et types de colonnes), puis m'envoient des fichiers CSV pour analyser et stocker. A partir des métadonnées stockées, je voudrais générer un modèle afin que je puisse utiliser Ecto pour gérer la table client et effectuer des requêtes à son encontre. Je viens d'un environnement Django où je peux utiliser la fonction intégrée ORM et type()
pour créer des modèles à la volée et les utiliser sans avoir à générer de migrations ou d'autres codes de modèles dans l'application.Modèles dynamiques dans le framework Phoenix
En Python, je (à peu près) faire:
class MetaModel(models.Model):
table_name = models.CharField(...)
model_name = models.CharField(...)
field_defs = JSONField(...)
def resolve_fields(self):
# takes values from `field_defs` and converts them into
# django field instances
def get_model(self):
class Meta:
app_label = 'dynamic'
db_table = self.table_name
fields = self.resolve_fields()
attrs = {'__module__': 'dynamic', 'Meta': Meta}
attrs.update(fields)
model = type(self.model_name, (models.Model,), attrs)
return model
def create_table(self):
with connection.schema_editor() as se:
model = self.get_model()
se.create_model(model)
Avec cela, je suis en mesure de créer la table dans la base de données, puis tirer parti de l'ORM de travailler avec des données fournies par des clients. Je sais que je peux le faire avec SQL brut et utiliser Ecto pour exécuter les commandes et les requêtes, mais je voudrais le rendre plus codifié et s'appuyer sur les internes d'Ecto plutôt que d'écrire et de maintenir un tas de SQL modèles
Un conseil (même un "non, vous ne pouvez pas faire cela") est super utile. Merci!
C'est vraiment cool, comment feriez-vous de redéfinir un module donné? – webdeb
Got it, vous pouvez simplement remplacer le module avec le même nom/atome – webdeb
Ceci est excellent! Merci beaucoup! – vforgione