Ticket #3070: django_management_sql.diff

File django_management_sql.diff, 7.4 KB (added by Bastian Kleineidam <calvin@…>, 18 years ago)
  • django/core/management.py

     
    33
    44import django
    55from django.core.exceptions import ImproperlyConfigured
    6 import os, re, shutil, sys, textwrap
     6import os, re, shutil, sys, textwrap, glob
    77from optparse import OptionParser
    88from django.utils import termcolors
    99
     
    330330get_sql_reset.help_doc = "Prints the DROP TABLE SQL, then the CREATE TABLE SQL, for the given app name(s)."
    331331get_sql_reset.args = APP_ARGS
    332332
    333 def get_sql_initial_data_for_model(model):
    334     from django.db import models
     333def flatten (listoflists):
     334    return [item for sublist in listoflists for item in sublist]
     335
     336def get_sql_initial_files_for_model (app_dir, model):
    335337    from django.conf import settings
    336338
    337339    opts = model._meta
    338     app_dir = os.path.normpath(os.path.join(os.path.dirname(models.get_app(model._meta.app_label).__file__), 'sql'))
     340    # Find custom SQL, if it's available.
     341    # Part one: using model names as filename.
     342    fnames = ["%s.%s.sql" % (opts.object_name.lower(), settings.DATABASE_ENGINE),
     343              "%s.sql" % opts.object_name.lower()]
     344    sql_files = [os.path.join(app_dir, fname) for fname in fnames]
     345    # Part two: using model names as suffix.
     346    fnames = flatten([glob.glob(os.path.join(app_dir, "*[._]%s" % fname))
     347                        for fname in fnames])
     348    sql_files.extend(fnames)
     349    return sql_files
     350
     351
     352def get_sql_initial_data_for_models(app_dir, models):
    339353    output = []
     354    sql_files = []
    340355
    341356    # Some backends can't execute more than one SQL statement at a time,
    342357    # so split into separate statements.
    343358    statements = re.compile(r";[ \t]*$", re.M)
    344359
    345     # Find custom SQL, if it's available.
    346     sql_files = [os.path.join(app_dir, "%s.%s.sql" % (opts.object_name.lower(), settings.DATABASE_ENGINE)),
    347                  os.path.join(app_dir, "%s.sql" % opts.object_name.lower())]
     360    for model in models:
     361        sql_files.extend(get_sql_initial_files_for_model(app_dir, model))
     362    sql_files.sort()
    348363    for sql_file in sql_files:
    349364        if os.path.exists(sql_file):
    350365            fp = open(sql_file, 'U')
     
    360375def get_sql_initial_data(app):
    361376    "Returns a list of the initial INSERT SQL statements for the given app."
    362377    from django.db.models import get_models
    363     output = []
    364378
    365379    app_models = get_models(app)
    366380    app_dir = os.path.normpath(os.path.join(os.path.dirname(app.__file__), 'sql'))
    367 
    368     for model in app_models:
    369         output.extend(get_sql_initial_data_for_model(model))
    370 
    371     return output
     381    return get_sql_initial_data_for_models(app_dir, app_models)
    372382get_sql_initial_data.help_doc = "Prints the initial INSERT SQL statements for the given app name(s)."
    373383get_sql_initial_data.args = APP_ARGS
    374384
     
    483493            if verbosity >= 1:
    484494                print "Creating table %s" % model._meta.db_table
    485495            for statement in sql:
     496                if verbosity >= 2:
     497                    print "SQL:", statement
    486498                cursor.execute(statement)
    487499            table_list.append(model._meta.db_table)
    488500
     
    493505                    if verbosity >= 2:
    494506                        print "Creating many-to-many tables for %s.%s model" % (app_name, model._meta.object_name)
    495507                    for statement in sql:
     508                        if verbosity >= 2:
     509                            print "SQL:", statement
    496510                        cursor.execute(statement)
    497511
    498512        transaction.commit_unless_managed()
     
    507521            app=app, created_models=created_models,
    508522            verbosity=verbosity, interactive=interactive)
    509523
     524        app_dir = os.path.normpath(os.path.join(os.path.dirname(app.__file__), 'sql'))
    510525        # Install initial data for the app (but only if this is a model we've
    511526        # just created)
    512         for model in models.get_models(app):
    513             if model in created_models:
    514                 initial_sql = get_sql_initial_data_for_model(model)
    515                 if initial_sql:
    516                     if verbosity >= 1:
    517                         print "Installing initial data for %s.%s model" % (app_name, model._meta.object_name)
    518                     try:
    519                         for sql in initial_sql:
    520                             cursor.execute(sql)
    521                     except Exception, e:
    522                         sys.stderr.write("Failed to install initial SQL data for %s.%s model: %s" % \
    523                                             (app_name, model._meta.object_name, e))
    524                         transaction.rollback_unless_managed()
    525                     else:
    526                         transaction.commit_unless_managed()
     527       
     528        newmodels = [m for m in models.get_models(app) if m in created_models]
     529        initial_sql = get_sql_initial_data_for_models(app_dir, newmodels)
     530        if initial_sql:
     531            modelnames = ["%s.%s" % (app_name, m.__name__) for m in newmodels]
     532            strmodelnames = ", ".join(modelnames)
     533            if verbosity >= 1:
     534                print "Installing initial data for models", strmodelnames
     535            try:
     536                for sql in initial_sql:
     537                    if verbosity >= 2:
     538                        print "SQL:", sql
     539                    cursor.execute(sql)
     540            except Exception, e:
     541                sys.stderr.write("Failed to install initial SQL data for models %s: %s" % \
     542                                 (strmodelnames, e))
     543                transaction.rollback_unless_managed()
     544            else:
     545                transaction.commit_unless_managed()
    527546
    528547    # Install SQL indicies for all newly created models
    529548    for app in models.get_apps():
     
    536555                        print "Installing index for %s.%s model" % (app_name, model._meta.object_name)
    537556                    try:
    538557                        for sql in index_sql:
     558                            if verbosity >= 2:
     559                                print "SQL:", sql
    539560                            cursor.execute(sql)
    540561                    except Exception, e:
    541562                        sys.stderr.write("Failed to install index for %s.%s model: %s" % \
     
    597618    print '\n'.join(output)
    598619diffsettings.args = ""
    599620
    600 def install(app):
     621def install(app, verbosity=1):
    601622    "Executes the equivalent of 'get_sql_all' in the current database."
    602623    from django.db import connection, transaction
    603624
     
    613634    try:
    614635        cursor = connection.cursor()
    615636        for sql in sql_list:
     637            if verbosity >= 2:
     638                print "SQL:", sql
    616639            cursor.execute(sql)
    617640    except Exception, e:
    618641        sys.stderr.write(style.ERROR("""Error: %s couldn't be installed. Possible reasons:
     
    627650install.help_doc = "Executes ``sqlall`` for the given app(s) in the current database."
    628651install.args = APP_ARGS
    629652
    630 def reset(app, interactive=True):
     653def reset(app, interactive=True, verbosity=1):
    631654    "Executes the equivalent of 'get_sql_reset' in the current database."
    632655    from django.db import connection, transaction
    633656    from django.conf import settings
     
    654677        try:
    655678            cursor = connection.cursor()
    656679            for sql in sql_list:
     680                if verbosity >= 2:
     681                    print "SQL:", sql
    657682                cursor.execute(sql)
    658683        except Exception, e:
    659684            sys.stderr.write(style.ERROR("""Error: %s couldn't be reset. Possible reasons:
Back to Top