#27267: Renaming a primary key fails with "cannot drop constraint on table 
because
other objects depend on it"
--------------------------------+--------------------------------------
     Reporter:  Melvyn Sopacua  |                    Owner:  nobody
         Type:  Bug             |                   Status:  new
    Component:  Migrations      |                  Version:  1.8
     Severity:  Normal          |               Resolution:
     Keywords:                  |             Triage Stage:  Unreviewed
    Has patch:  0               |      Needs documentation:  0
  Needs tests:  0               |  Patch needs improvement:  0
Easy pickings:  0               |                    UI/UX:  0
--------------------------------+--------------------------------------

Comment (by Melvyn Sopacua):

 Setting preserve_default to True or omitting the keyword argument still
 results in the DROP DEFAULT statement being emitted. I executed the
 statements from sqlmigrate without the DROP DEFAULT part to get out of the
 catch-22. As you can see in the initial comment this was also a table that
 ran into the drop contraint error.

 I'm still baffled what makes this model and the item model different so
 that we can get to the root cause.

 For completeness here's the model definition:

 {{{#!python
 class DpeCharacter(
     uni_factory(max_length=32, verbose_name=_('name of character'))
 ):
     character_id = models.AutoField(primary_key=True)
     char_class = models.ForeignKey(
         CharacterClass, related_name='class_characters',
     )
     account = models.ForeignKey(
         'DpeAccount', models.CASCADE,
         related_name='my_characters',
         null=True, blank=True,
     )
     level = models.PositiveSmallIntegerField(
         verbose_name=_('current level'),
         validators=(
             MinValueValidator(1, 'Minimum level is 1'),
             MaxValueValidator(105, 'Maximum level is 105'),
         )
     )
     avatar = models.ImageField(
         verbose_name=_('avatar picture'),
         help_text=_('Square JPEG or PNG format, min 32x32, max 128x128
 pixels'),
         upload_to=avatar_upload_to,
         height_field='avatar_height',
         width_field='avatar_width',
         null=True, blank=True,
     )
     avatar_height = models.PositiveSmallIntegerField(
         validators=(
             MinValueValidator(32, 'Avatar image too small.'),
             MaxValueValidator(128, 'Avatar image too tall.'),
         ),
         null=True, blank=True,
     )
     avatar_width = models.PositiveSmallIntegerField(
         validators=(
             MinValueValidator(32, 'Avatar image too narrow'),
             MaxValueValidator(128, 'Avatar image too wide'),
         ),
         null=True, blank=True,
     )

     def __str__(self):
         return '{} ({}-{})'.format(
             self.name, self.char_class.abbreviation, self.level
         )

     def clean(self):
         if self.avatar is not None:
             if self.avatar_height != self.avatar_width:
                 raise ValidationError({'avatar': 'Image should be
 square'})

     class Meta:
         verbose_name = _('character')
         verbose_name_plural = _('characters')
         app_label = 'dpe'
 }}}

 And uni_factory:
 {{{#!python
 class UniquelyNamedItemManager(models.Manager):
     def get_by_natural_key(self, name):
         return self.get(name=name)


 class PagedUniquelyNamedItemManager(PageManager,
 UniquelyNamedItemManager):
     pass


 def uni_factory(**kwargs):
     defaults = {
         'verbose_name': _('name'),
         'help_text': _('must be unique'),
         'is_paged': False,
     }
     defaults.update(kwargs)
     if defaults.pop('is_paged', False):
         manager = PagedUniquelyNamedItemManager
     else:
         manager = UniquelyNamedItemManager

     class UniquelyNamedItemMixin(models.Model):
         objects = manager()
         name = UniqueNameField(**defaults)

         def __str__(self):
             return self.name

         def natural_key(self):
             return self.name

         class Meta(models.base.ModelBase):
             app_label = 'dpe'
             abstract = True

     return UniquelyNamedItemMixin
 }}}

 And finally, UniqueNameFIeld:
 {{{#!
 class UniqueNameField(CharField):
     title_transform = True
     max_length = 63

     def __init__(self, title_transform=True, *args, **kwargs):
         kwargs['unique'] = True
         kwargs['max_length'] = kwargs.get('max_length', self.max_length)
         self.title_transform = title_transform
         super(UniqueNameField, self).__init__(*args, **kwargs)

     def deconstruct(self):
         name, path, args, kwargs = super(CharField, self).deconstruct()
         kwargs['title_transform'] = self.title_transform
         return name, path, args, kwargs

     def pre_save(self, model_instance, add):
         name = super(UniqueNameField, self).pre_save(model_instance, add)
         if self.title_transform:
             name = name.title()
             setattr(model_instance, self.name, name)
         return name
 }}}

--
Ticket URL: <https://code.djangoproject.com/ticket/27267#comment:12>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.

-- 
You received this message because you are subscribed to the Google Groups 
"Django updates" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-updates/072.dd5cc57811feb8550d7f3034cca698e6%40djangoproject.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to