def handle_app(self, app, **options):
     appname = app.__name__
     print 'handling app %s' % appname
     for obj in [getattr(app, name) for name in dir(app)]:
         if not isclass(obj):
             continue
         if not issubclass(obj, models.Model):
             continue
         if not is_multilingual_model(obj):
             continue
         print 'altering model %s' % obj
         table = obj._meta.translation_model._meta.db_table
         db.debug = True
         db.add_column(table, 
             'language_code',
             models.CharField(max_length=15, blank=True,
                 choices=get_language_choices(), db_index=True)
         )
         # migrate the model
         # This is TERRIBLE for performance, but whatever...
         print 'migrating data'
         tempfield = models.IntegerField(blank=False, null=False,
             choices=get_language_choices(), db_index=False)
         tempfield.contribute_to_class(obj._meta.translation_model, 'language_id')
         for row in obj.objects.all():
             for translation in row.translations.all():
                 translation.language_code = get_code_by_id(translation.language_id)
                 translation.save()
         db.create_index(table, ['language_code', 'master_id'])
         print 'deleting language_id column'
         db.delete_unique(table, ['language_id', 'master_id'])
         db.delete_column(table, 'language_id')
Esempio n. 2
0
def validate_admin_registration(cls, model):
    """
    Validates a class specified as a model admin.

    Right now this means validating prepopulated_fields, as for
    multilingual models DM handles them by itself.
    """

    if not is_multilingual_model(model):
        return

    from django.contrib.admin.validation import check_isdict, check_isseq

    opts = model._meta

    # this is heavily based on django.contrib.admin.validation.
    if hasattr(cls, '_dm_prepopulated_fields'):
        check_isdict(cls, '_dm_prepopulated_fields', cls.prepopulated_fields)
        for field, val in cls._dm_prepopulated_fields.items():
            f = get_field(cls, model, opts, 'prepopulated_fields', field)
            if isinstance(f, (models.DateTimeField, models.ForeignKey,
                              models.ManyToManyField)):
                raise ImproperlyConfigured(
                    "'%s.prepopulated_fields['%s']' "
                    "is either a DateTimeField, ForeignKey or "
                    "ManyToManyField. This isn't allowed." %
                    (cls.__name__, field))
            check_isseq(cls, "prepopulated_fields['%s']" % field, val)
            for idx, f in enumerate(val):
                get_field(cls, model, opts,
                          "prepopulated_fields['%s'][%d]" % (f, idx), f)
Esempio n. 3
0
def validate_admin_registration(cls, model):
    """
    Validates a class specified as a model admin.

    Right now this means validating prepopulated_fields, as for
    multilingual models DM handles them by itself.
    """

    if not is_multilingual_model(model):
        return

    from django.contrib.admin.validation import check_isdict, check_isseq

    opts = model._meta

    # this is heavily based on django.contrib.admin.validation.
    if hasattr(cls, '_dm_prepopulated_fields'):
        check_isdict(cls, '_dm_prepopulated_fields', cls.prepopulated_fields)
        for field, val in cls._dm_prepopulated_fields.items():
            f = get_field(cls, model, opts, 'prepopulated_fields', field)
            if isinstance(f, (models.DateTimeField, models.ForeignKey,
                models.ManyToManyField)):
                raise ImproperlyConfigured("'%s.prepopulated_fields['%s']' "
                        "is either a DateTimeField, ForeignKey or "
                        "ManyToManyField. This isn't allowed."
                        % (cls.__name__, field))
            check_isseq(cls, "prepopulated_fields['%s']" % field, val)
            for idx, f in enumerate(val):
                get_field(cls, model,
                        opts, "prepopulated_fields['%s'][%d]"
                        % (f, idx), f)
 def handle_app(self, app, **options):
     appname = app.__name__
     print 'handling app %s' % appname
     for obj in [getattr(app, name) for name in dir(app)]:
         if not isclass(obj):
             continue
         if not issubclass(obj, models.Model):
             continue
         if not is_multilingual_model(obj):
             continue
         print 'altering model %s' % obj
         table = obj._meta.translation_model._meta.db_table
         db.debug = True
         # do this in a transaction
         db.start_transaction()
         # first add the column with nullable values, and no index
         lc_field = models.CharField(max_length=15, blank=True, null=True)
         db.add_column(table, 'language_code', lc_field)
         # migrate the model
         print 'migrating data'
         # do the conversion server-side
         # all modern RDBMSs support the case statement
         update_sql = "UPDATE %s SET language_code = (CASE language_id %s END)" % (table, 
             ' '.join(
                 "WHEN %d THEN '%s'" % (lid, get_code_by_id(lid))
                 for lid in range(1, len(settings.LANGUAGES) + 1)
                 )
             )
         db.execute(update_sql)
         print 'deleting language_id column'
         db.delete_unique(table, ['language_id', 'master_id'])
         db.delete_column(table, 'language_id')
         print 'setting up constraints and indices'
         # alter the column to set not null
         lc_field.null = False
         db.alter_column(table, 'language_code', lc_field)
         ## we don't really need this indexed. all queries should hit the unique index
         #db.create_index(table, ['language_code'])
         # and create a unique index for master & language
         db.create_unique(table, ['language_code', 'master_id'])
         # south might fail to commit if we don't do it explicitly
         db.commit_transaction()
Esempio n. 5
0
 def handle_app(self, app, **options):
     appname = app.__name__
     print 'handling app %s' % appname
     for obj in [getattr(app, name) for name in dir(app)]:
         if not isclass(obj):
             continue
         if not issubclass(obj, models.Model):
             continue
         if not is_multilingual_model(obj):
             continue
         print 'altering model %s' % obj
         table = obj._meta.translation_model._meta.db_table
         db.debug = True
         # do this in a transaction
         db.start_transaction()
         # first add the column with nullable values, and no index
         lc_field = models.CharField(max_length=15, blank=True, null=True)
         db.add_column(table, 'language_code', lc_field)
         # migrate the model
         print 'migrating data'
         # do the conversion server-side
         # all modern RDBMSs support the case statement
         update_sql = "UPDATE %s SET language_code = (CASE language_id %s END)" % (
             table, ' '.join("WHEN %d THEN '%s'" %
                             (lid, get_code_by_id(lid))
                             for lid in range(1,
                                              len(settings.LANGUAGES) + 1)))
         db.execute(update_sql)
         print 'deleting language_id column'
         db.delete_unique(table, ['language_id', 'master_id'])
         db.delete_column(table, 'language_id')
         print 'setting up constraints and indices'
         # alter the column to set not null
         lc_field.null = False
         db.alter_column(table, 'language_code', lc_field)
         ## we don't really need this indexed. all queries should hit the unique index
         #db.create_index(table, ['language_code'])
         # and create a unique index for master & language
         db.create_unique(table, ['language_code', 'master_id'])
         # south might fail to commit if we don't do it explicitly
         db.commit_transaction()