def contribute_to_class(self, cls, *args, **kwargs): super().contribute_to_class(cls, *args, **kwargs) # Add any necessary unique_together index to the model if self.unique_for_fields and self.unique_db_constraint: # Alter only original_attr to fake being a declared unique_together # Cannot modify cls._meta.unique_together as it breaks state consistency for migrations ut = set((self.unique_together, )).union( normalize_together( cls._meta.original_attrs.get('unique_together'))) cls._meta.original_attrs['unique_together'] = ut
def __init__(self, name, unique_together): unique_together = normalize_together(unique_together) self.unique_together = set(tuple(cons) for cons in unique_together) super(AlterUniqueTogether, self).__init__(name)
def from_model(cls, model, exclude_rels=False): """ Feed me a model, get a ModelState representing it out. """ # Deconstruct the fields fields = [] for field in model._meta.local_fields: if getattr(field, "rel", None) and exclude_rels: continue if isinstance(field, OrderWrt): continue name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct field %s on %s.%s: %s" % ( name, model._meta.app_label, model._meta.object_name, e, )) if not exclude_rels: for field in model._meta.local_many_to_many: name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct m2m field %s on %s: %s" % ( name, model._meta.object_name, e, )) # Extract the options options = {} for name in DEFAULT_NAMES: # Ignore some special options if name in ["apps", "app_label"]: continue elif name in model._meta.original_attrs: if name == "unique_together": ut = model._meta.original_attrs["unique_together"] options[name] = set(normalize_together(ut)) elif name == "index_together": it = model._meta.original_attrs["index_together"] options[name] = set(normalize_together(it)) else: options[name] = model._meta.original_attrs[name] # If we're ignoring relationships, remove all field-listing model # options (that option basically just means "make a stub model") if exclude_rels: for key in ["unique_together", "index_together", "order_with_respect_to"]: if key in options: del options[key] def flatten_bases(model): bases = [] for base in model.__bases__: if hasattr(base, "_meta") and base._meta.abstract: bases.extend(flatten_bases(base)) else: bases.append(base) return bases # We can't rely on __mro__ directly because we only want to flatten # abstract models and not the whole tree. However by recursing on # __bases__ we may end up with duplicates and ordering issues, we # therefore discard any duplicates and reorder the bases according # to their index in the MRO. flattened_bases = sorted(set(flatten_bases(model)), key=lambda x: model.__mro__.index(x)) # Make our record bases = tuple( ( "%s.%s" % (base._meta.app_label, base._meta.model_name) if hasattr(base, "_meta") else base ) for base in flattened_bases ) # Ensure at least one base inherits from models.Model if not any((isinstance(base, six.string_types) or issubclass(base, models.Model)) for base in bases): bases = (models.Model,) return cls( model._meta.app_label, model._meta.object_name, fields, options, bases, )
def from_model(cls, model, exclude_rels=False): """ Feed me a model, get a ModelState representing it out. """ # Deconstruct the fields fields = [] for field in model._meta.local_fields: if getattr(field, "rel", None) and exclude_rels: continue if isinstance(field, OrderWrt): continue name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct field %s on %s.%s: %s" % ( name, model._meta.app_label, model._meta.object_name, e, )) if not exclude_rels: for field in model._meta.local_many_to_many: name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError( "Couldn't reconstruct m2m field %s on %s: %s" % ( name, model._meta.object_name, e, )) # Extract the options options = {} for name in DEFAULT_NAMES: # Ignore some special options if name in ["apps", "app_label"]: continue elif name in model._meta.original_attrs: if name == "unique_together": ut = model._meta.original_attrs["unique_together"] options[name] = set(normalize_together(ut)) elif name == "index_together": it = model._meta.original_attrs["index_together"] options[name] = set(normalize_together(it)) else: options[name] = model._meta.original_attrs[name] # If we're ignoring relationships, remove all field-listing model # options (that option basically just means "make a stub model") if exclude_rels: for key in [ "unique_together", "index_together", "order_with_respect_to" ]: if key in options: del options[key] def flatten_bases(model): bases = [] for base in model.__bases__: if hasattr(base, "_meta") and base._meta.abstract: bases.extend(flatten_bases(base)) else: bases.append(base) return bases # We can't rely on __mro__ directly because we only want to flatten # abstract models and not the whole tree. However by recursing on # __bases__ we may end up with duplicates and ordering issues, we # therefore discard any duplicates and reorder the bases according # to their index in the MRO. flattened_bases = sorted(set(flatten_bases(model)), key=lambda x: model.__mro__.index(x)) # Make our record bases = tuple( ("%s.%s" % (base._meta.app_label, base._meta.model_name) if hasattr(base, "_meta") else base) for base in flattened_bases) # Ensure at least one base inherits from models.Model if not any((isinstance(base, six.string_types) or issubclass(base, models.Model)) for base in bases): bases = (models.Model, ) return cls( model._meta.app_label, model._meta.object_name, fields, options, bases, )
def __init__(self, name, index_together): index_together = normalize_together(index_together) self.index_together = set(tuple(cons) for cons in index_together) super(AlterIndexTogether, self).__init__(name)
def __init__(self, name, index_together): self.name = name index_together = normalize_together(index_together) self.index_together = set(tuple(cons) for cons in index_together)
def __init__(self, name, index_together): index_together = normalize_together(index_together) self.index_together = {tuple(cons) for cons in index_together} super().__init__(name)
def __init__(self, name, index_together): self.name = name index_together = normalize_together(index_together) # need None rather than an empty set to prevent infinite migrations # after removing unique_together from a model self.index_together = set(tuple(cons) for cons in index_together) or None
def __init__(self, name, unique_together): unique_together = normalize_together(unique_together) self.unique_together = {tuple(cons) for cons in unique_together} super().__init__(name)
from __future__ import unicode_literals
def __init__(self, name, option_value): if option_value: option_value = set(normalize_together(option_value)) setattr(self, self.option_name, option_value) super().__init__(name)
def from_model(cls, model): """ Feed me a model, get a ModelState representing it out. """ # Deconstruct the fields fields = [] for field in model._meta.local_fields: name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct field %s on %s.%s: %s" % ( name, model._meta.app_label, model._meta.object_name, e, )) for field in model._meta.local_many_to_many: name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct m2m field %s on %s: %s" % ( name, model._meta.object_name, e, )) # Extract the options options = {} for name in DEFAULT_NAMES: # Ignore some special options if name in ["apps", "app_label"]: continue elif name in model._meta.original_attrs: if name == "unique_together": ut = model._meta.original_attrs["unique_together"] options[name] = set(normalize_together(ut)) elif name == "index_together": it = model._meta.original_attrs["index_together"] options[name] = set(normalize_together(it)) else: options[name] = model._meta.original_attrs[name] # Make our record bases = tuple( ( "%s.%s" % (base._meta.app_label, base._meta.model_name) if hasattr(base, "_meta") else base ) for base in model.__bases__ if (not hasattr(base, "_meta") or not base._meta.abstract) ) # Ensure at least one base inherits from models.Model if not any((isinstance(base, six.string_types) or issubclass(base, models.Model)) for base in bases): bases = (models.Model, ) return cls( model._meta.app_label, model._meta.object_name, fields, options, bases, )
def from_model(cls, model, exclude_rels=False): """ Feed me a model, get a ModelState representing it out. """ # Deconstruct the fields fields = [] for field in model._meta.local_fields: if getattr(field, "remote_field", None) and exclude_rels: continue if isinstance(field, OrderWrt): continue name = force_text(field.name, strings_only=True) try: fields.append((name, field.clone())) except TypeError as e: raise TypeError("Couldn't reconstruct field %s on %s: %s" % ( name, model._meta.label, e, )) if not exclude_rels: for field in model._meta.local_many_to_many: name = force_text(field.name, strings_only=True) try: fields.append((name, field.clone())) except TypeError as e: raise TypeError("Couldn't reconstruct m2m field %s on %s: %s" % ( name, model._meta.object_name, e, )) # Extract the options options = {} for name in DEFAULT_NAMES: # Ignore some special options if name in ["apps", "app_label"]: continue elif name in model._meta.original_attrs: if name == "unique_together": ut = model._meta.original_attrs["unique_together"] options[name] = set(normalize_together(ut)) elif name == "index_together": it = model._meta.original_attrs["index_together"] options[name] = set(normalize_together(it)) else: options[name] = model._meta.original_attrs[name] # Force-convert all options to text_type (#23226) options = cls.force_text_recursive(options) # If we're ignoring relationships, remove all field-listing model # options (that option basically just means "make a stub model") if exclude_rels: for key in ["unique_together", "index_together", "order_with_respect_to"]: if key in options: del options[key] # Private fields are ignored, so remove options that refer to them. elif options.get('order_with_respect_to') in {field.name for field in model._meta.private_fields}: del options['order_with_respect_to'] def flatten_bases(model): bases = [] for base in model.__bases__: if hasattr(base, "_meta") and base._meta.abstract: bases.extend(flatten_bases(base)) else: bases.append(base) return bases # We can't rely on __mro__ directly because we only want to flatten # abstract models and not the whole tree. However by recursing on # __bases__ we may end up with duplicates and ordering issues, we # therefore discard any duplicates and reorder the bases according # to their index in the MRO. flattened_bases = sorted(set(flatten_bases(model)), key=lambda x: model.__mro__.index(x)) # Make our record bases = tuple( ( base._meta.label_lower if hasattr(base, "_meta") else base ) for base in flattened_bases ) # Ensure at least one base inherits from models.Model if not any((isinstance(base, six.string_types) or issubclass(base, models.Model)) for base in bases): bases = (models.Model,) managers = [] manager_names = set() default_manager_shim = None for manager in model._meta.managers: manager_name = force_text(manager.name) if manager_name in manager_names: # Skip overridden managers. continue elif manager.use_in_migrations: # Copy managers usable in migrations. new_manager = copy.copy(manager) new_manager._set_creation_counter() elif manager is model._base_manager or manager is model._default_manager: # Shim custom managers used as default and base managers. new_manager = models.Manager() new_manager.model = manager.model new_manager.name = manager.name if manager is model._default_manager: default_manager_shim = new_manager else: continue manager_names.add(manager_name) managers.append((manager_name, new_manager)) # Ignore a shimmed default manager called objects if it's the only one. if managers == [('objects', default_manager_shim)]: managers = [] # Construct the new ModelState return cls( model._meta.app_label, model._meta.object_name, fields, options, bases, managers, )
def __init__(self, name, unique_together): self.name = name unique_together = normalize_together(unique_together) self.unique_together = set(tuple(cons) for cons in unique_together)
def from_model(cls, model, exclude_rels=False): """ Feed me a model, get a ModelState representing it out. """ # Deconstruct the fields fields = [] for field in model._meta.local_fields: if getattr(field, "remote_field", None) and exclude_rels: continue if isinstance(field, OrderWrt): continue name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct field %s on %s.%s: %s" % ( name, model._meta.app_label, model._meta.object_name, e, )) if not exclude_rels: for field in model._meta.local_many_to_many: name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct m2m field %s on %s: %s" % ( name, model._meta.object_name, e, )) # Extract the options options = {} for name in DEFAULT_NAMES: # Ignore some special options if name in ["apps", "app_label"]: continue elif name in model._meta.original_attrs: if name == "unique_together": ut = model._meta.original_attrs["unique_together"] options[name] = set(normalize_together(ut)) elif name == "index_together": it = model._meta.original_attrs["index_together"] options[name] = set(normalize_together(it)) else: options[name] = model._meta.original_attrs[name] # Force-convert all options to text_type (#23226) options = cls.force_text_recursive(options) # If we're ignoring relationships, remove all field-listing model # options (that option basically just means "make a stub model") if exclude_rels: for key in ["unique_together", "index_together", "order_with_respect_to"]: if key in options: del options[key] def flatten_bases(model): bases = [] for base in model.__bases__: if hasattr(base, "_meta") and base._meta.abstract: bases.extend(flatten_bases(base)) else: bases.append(base) return bases # We can't rely on __mro__ directly because we only want to flatten # abstract models and not the whole tree. However by recursing on # __bases__ we may end up with duplicates and ordering issues, we # therefore discard any duplicates and reorder the bases according # to their index in the MRO. flattened_bases = sorted(set(flatten_bases(model)), key=lambda x: model.__mro__.index(x)) # Make our record bases = tuple( ( "%s.%s" % (base._meta.app_label, base._meta.model_name) if hasattr(base, "_meta") else base ) for base in flattened_bases ) # Ensure at least one base inherits from models.Model if not any((isinstance(base, six.string_types) or issubclass(base, models.Model)) for base in bases): bases = (models.Model,) # Constructs all managers on the model managers = {} def reconstruct_manager(mgr): as_manager, manager_path, qs_path, args, kwargs = mgr.deconstruct() if as_manager: qs_class = import_string(qs_path) instance = qs_class.as_manager() else: manager_class = import_string(manager_path) instance = manager_class(*args, **kwargs) # We rely on the ordering of the creation_counter of the original # instance managers[mgr.name] = (mgr.creation_counter, instance) if hasattr(model, "_default_manager"): default_manager_name = model._default_manager.name # Make sure the default manager is always the first if model._default_manager.use_in_migrations: reconstruct_manager(model._default_manager) else: # Force this manager to be the first and thus default managers[default_manager_name] = (0, models.Manager()) # Sort all managers by their creation counter for _, manager, _ in sorted(model._meta.managers): if manager.name == "_base_manager" or not manager.use_in_migrations: continue reconstruct_manager(manager) # Sort all managers by their creation counter but take only name and # instance for further processing managers = [ (name, instance) for name, (cc, instance) in sorted(managers.items(), key=lambda v: v[1]) ] if managers == [(default_manager_name, models.Manager())]: managers = [] else: managers = [] # Construct the new ModelState return cls( model._meta.app_label, model._meta.object_name, fields, options, bases, managers, )
def from_model(cls, model, exclude_rels=False): """ Feed me a model, get a ModelState representing it out. """ # Deconstruct the fields fields = [] for field in model._meta.local_fields: if getattr(field, "remote_field", None) and exclude_rels: continue if isinstance(field, OrderWrt): continue name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct field %s on %s: %s" % ( name, model._meta.label, e, )) if not exclude_rels: for field in model._meta.local_many_to_many: name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct m2m field %s on %s: %s" % ( name, model._meta.object_name, e, )) # Extract the options options = {} for name in DEFAULT_NAMES: # Ignore some special options if name in ["apps", "app_label"]: continue elif name in model._meta.original_attrs: if name == "unique_together": ut = model._meta.original_attrs["unique_together"] options[name] = set(normalize_together(ut)) elif name == "index_together": it = model._meta.original_attrs["index_together"] options[name] = set(normalize_together(it)) else: options[name] = model._meta.original_attrs[name] # Force-convert all options to text_type (#23226) options = cls.force_text_recursive(options) # If we're ignoring relationships, remove all field-listing model # options (that option basically just means "make a stub model") if exclude_rels: for key in ["unique_together", "index_together", "order_with_respect_to"]: if key in options: del options[key] def flatten_bases(model): bases = [] for base in model.__bases__: if hasattr(base, "_meta") and base._meta.abstract: bases.extend(flatten_bases(base)) else: bases.append(base) return bases # We can't rely on __mro__ directly because we only want to flatten # abstract models and not the whole tree. However by recursing on # __bases__ we may end up with duplicates and ordering issues, we # therefore discard any duplicates and reorder the bases according # to their index in the MRO. flattened_bases = sorted(set(flatten_bases(model)), key=lambda x: model.__mro__.index(x)) # Make our record bases = tuple( ( base._meta.label_lower if hasattr(base, "_meta") else base ) for base in flattened_bases ) # Ensure at least one base inherits from models.Model if not any((isinstance(base, six.string_types) or issubclass(base, models.Model)) for base in bases): bases = (models.Model,) # Constructs all managers on the model managers_mapping = {} def reconstruct_manager(mgr): as_manager, manager_path, qs_path, args, kwargs = mgr.deconstruct() if as_manager: qs_class = import_string(qs_path) instance = qs_class.as_manager() else: manager_class = import_string(manager_path) instance = manager_class(*args, **kwargs) # We rely on the ordering of the creation_counter of the original # instance name = force_text(mgr.name) managers_mapping[name] = (mgr.creation_counter, instance) if hasattr(model, "_default_manager"): default_manager_name = force_text(model._default_manager.name) # Make sure the default manager is always the first if model._default_manager.use_in_migrations: reconstruct_manager(model._default_manager) else: # Force this manager to be the first and thus default managers_mapping[default_manager_name] = (0, models.Manager()) # Sort all managers by their creation counter for _, manager, _ in sorted(model._meta.managers): if manager.name == "_base_manager" or not manager.use_in_migrations: continue reconstruct_manager(manager) # Sort all managers by their creation counter but take only name and # instance for further processing managers = [ (name, instance) for name, (cc, instance) in sorted(managers_mapping.items(), key=lambda v: v[1]) ] if managers == [(default_manager_name, models.Manager())]: managers = [] else: managers = [] # Construct the new ModelState return cls( model._meta.app_label, model._meta.object_name, fields, options, bases, managers, )
def from_model(cls, model, exclude_rels=False): """Given a model, return a ModelState representing it.""" # Deconstruct the fields fields = [] for field in model._meta.local_fields: if getattr(field, "remote_field", None) and exclude_rels: continue if isinstance(field, OrderWrt): continue name = field.name try: fields.append((name, field.clone())) except TypeError as e: raise TypeError("Couldn't reconstruct field %s on %s: %s" % ( name, model._meta.label, e, )) if not exclude_rels: for field in model._meta.local_many_to_many: name = field.name try: fields.append((name, field.clone())) except TypeError as e: raise TypeError( "Couldn't reconstruct m2m field %s on %s: %s" % ( name, model._meta.object_name, e, )) # Extract the options options = {} for name in DEFAULT_NAMES: # Ignore some special options if name in ["apps", "app_label"]: continue elif name in model._meta.original_attrs: if name == "unique_together": ut = model._meta.original_attrs["unique_together"] options[name] = set(normalize_together(ut)) elif name == "index_together": it = model._meta.original_attrs["index_together"] options[name] = set(normalize_together(it)) elif name == "indexes": indexes = [idx.clone() for idx in model._meta.indexes] for index in indexes: if not index.name: index.set_name_with_model(model) options['indexes'] = indexes else: options[name] = model._meta.original_attrs[name] # If we're ignoring relationships, remove all field-listing model # options (that option basically just means "make a stub model") if exclude_rels: for key in [ "unique_together", "index_together", "order_with_respect_to" ]: if key in options: del options[key] # Private fields are ignored, so remove options that refer to them. elif options.get('order_with_respect_to') in { field.name for field in model._meta.private_fields }: del options['order_with_respect_to'] def flatten_bases(model): bases = [] for base in model.__bases__: if hasattr(base, "_meta") and base._meta.abstract: bases.extend(flatten_bases(base)) else: bases.append(base) return bases # We can't rely on __mro__ directly because we only want to flatten # abstract models and not the whole tree. However by recursing on # __bases__ we may end up with duplicates and ordering issues, we # therefore discard any duplicates and reorder the bases according # to their index in the MRO. flattened_bases = sorted(set(flatten_bases(model)), key=lambda x: model.__mro__.index(x)) # Make our record bases = tuple( (base._meta.label_lower if hasattr(base, "_meta") else base) for base in flattened_bases) # Ensure at least one base inherits from models.Model if not any((isinstance(base, str) or issubclass(base, models.Model)) for base in bases): bases = (models.Model, ) managers = [] manager_names = set() default_manager_shim = None for manager in model._meta.managers: if manager.name in manager_names: # Skip overridden managers. continue elif manager.use_in_migrations: # Copy managers usable in migrations. new_manager = copy.copy(manager) new_manager._set_creation_counter() elif manager is model._base_manager or manager is model._default_manager: # Shim custom managers used as default and base managers. new_manager = models.Manager() new_manager.model = manager.model new_manager.name = manager.name if manager is model._default_manager: default_manager_shim = new_manager else: continue manager_names.add(manager.name) managers.append((manager.name, new_manager)) # Ignore a shimmed default manager called objects if it's the only one. if managers == [('objects', default_manager_shim)]: managers = [] # Construct the new ModelState return cls( model._meta.app_label, model._meta.object_name, fields, options, bases, managers, )
def from_model(cls, model): """ Feed me a model, get a ModelState representing it out. """ # Deconstruct the fields fields = [] for field in model._meta.local_fields: name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct field %s on %s.%s: %s" % ( name, model._meta.app_label, model._meta.object_name, e, )) for field in model._meta.local_many_to_many: name, path, args, kwargs = field.deconstruct() field_class = import_string(path) try: fields.append((name, field_class(*args, **kwargs))) except TypeError as e: raise TypeError("Couldn't reconstruct m2m field %s on %s: %s" % ( name, model._meta.object_name, e, )) # Extract the options options = {} for name in DEFAULT_NAMES: # Ignore some special options if name in ["apps", "app_label"]: continue elif name in model._meta.original_attrs: if name == "unique_together": ut = model._meta.original_attrs["unique_together"] options[name] = set(normalize_together(ut)) elif name == "index_together": it = model._meta.original_attrs["index_together"] options[name] = set(normalize_together(it)) else: options[name] = model._meta.original_attrs[name] # Make our record bases = tuple( ("%s.%s" % (base._meta.app_label, base._meta.model_name) if hasattr(base, "_meta") else base) for base in model.__bases__ if (not hasattr(base, "_meta") or not base._meta.abstract)) # Ensure at least one base inherits from models.Model if not any((isinstance(base, six.string_types) or issubclass(base, models.Model)) for base in bases): bases = (models.Model, ) return cls( model._meta.app_label, model._meta.object_name, fields, options, bases, )