2010-10-11 45 views
3

Je cherchais un moyen de définir des tables de base de données et de les modifier via une API Django. Par exemple, je voudrais écrire du code qui manipule directement la table DDL et permette de définir des tables ou d'ajouter des colonnes à une table à la demande par programmation (sans exécuter de syncdb). Je me rends compte que django-sud et django-evolution peuvent venir à l'esprit, mais je ne pense pas vraiment à ces outils comme outils destinés à être intégrés dans une application et utilisés par l'utilisateur final ... ces outils sont plutôt utilisés pour mettre à jour vos tables de base de données. Je cherche quelque chose où je peux faire quelque chose comme:Django créer/modifier des tables à la demande

class MyModel(models.Model): # wouldn't run syncdb.. instead do something like below 
    a = models.CharField() 
    b = models.CharField() 

model = MyModel() 
model.create() # this runs the create table (instead of a syncdb) 

model.add_column(c = models.CharField()) # this would set a column to be added 
model.alter() # and this would apply the alter statement 

model.del_column('a') # this would set column 'a' for removal 
model.alter() # and this would apply the removal 

Ceci est juste un exemple de jouet de la façon dont une telle API fonctionnerait, mais le point est que je serais très intéressé à savoir s'il est un moyen de créer et de modifier par programme des tableaux comme celui-ci. Cela peut être utile pour des choses telles que les systèmes de gestion de contenu, où l'on peut vouloir créer dynamiquement une nouvelle table. Un autre exemple serait un site qui stocke des ensembles de données d'une largeur arbitraire, pour lesquels les tables doivent être générées dynamiquement par l'interface ou les importations de données. Quelqu'un sait-il de bons moyens de créer et de modifier dynamiquement des tableaux comme celui-ci?

(D'accord, je sais que l'on peut faire des déclarations SQL directes contre la base de données, mais cette solution n'a pas la capacité de traiter les bases de données sous forme d'objets)

curieux de si les gens ont des suggestions ou approches à cet égard. ..

Répondre

1

Vous pouvez essayer de vous interfacer avec le code de django qui gère les modifications dans la base de données. C'est un peu limité (pas de ALTER, par exemple, pour autant que je puisse le voir), mais vous pourrez peut-être l'étendre. Voici un extrait de django.core.management.commands.syncdb.

for app in models.get_apps(): 
     app_name = app.__name__.split('.')[-2] 
     model_list = models.get_models(app) 
     for model in model_list: 
      # Create the model's database table, if it doesn't already exist. 
      if verbosity >= 2: 
       print "Processing %s.%s model" % (app_name, model._meta.object_name) 
      if connection.introspection.table_name_converter(model._meta.db_table) in tables: 
       continue 
      sql, references = connection.creation.sql_create_model(model, self.style, seen_models) 
      seen_models.add(model) 
      created_models.add(model) 
      for refto, refs in references.items(): 
       pending_references.setdefault(refto, []).extend(refs) 
       if refto in seen_models: 
        sql.extend(connection.creation.sql_for_pending_references(refto, self.style, pending_references)) 
      sql.extend(connection.creation.sql_for_pending_references(model, self.style, pending_references)) 
      if verbosity >= 1 and sql: 
       print "Creating table %s" % model._meta.db_table 
      for statement in sql: 
       cursor.execute(statement) 
      tables.append(connection.introspection.table_name_converter(model._meta.db_table)) 

Regardez connection.creation.sql_create_model. L'objet creation est créé dans le backend de base de données correspondant à la base de données que vous utilisez dans votre fichier settings.py. Tous sont sous django.db.backends.

Si vous devez avoir une table ALTER, je pense que vous pouvez créer votre propre backend personnalisé qui en étend un existant et ajoute cette fonctionnalité. Vous pouvez ensuite vous interfacer directement avec un ExtendedModelManager que vous créez.

+0

OmerGertel, merci pour cette approche. Je vais devoir creuser pour voir si je peux l'étendre pour faire des changements comme vous le suggérez. Mon rêve serait d'avoir Django (ou au moins mon extension) capable de supporter "créer, modifier, tronquer, etc". Je pense que cela ouvrirait un tout nouveau domaine d'utilisations pour cela. Merci encore pour vos commentaires et vos pensées. –

2

rapidement du haut de ma tête ..

Créez un gestionnaire personnalisé avec les méthodes Création/modification.

+1

Merci pour votre conseil, Rasiel. Je suppose que j'espérais que je n'aurais pas à coder en dur SQL dans un gestionnaire ou quelque chose comme ça. Après tout, si syncdb peut émettre des instructions CREATE, on peut espérer qu'il peut être appelé manuellement. Cependant, cette utilisation de DDL SQL dans Django est peut-être quelque chose que la plupart des gens n'ont pas envie de faire. –