magic-removal: Changed ManyToOne, ManyToMany and OneToOne to store the model class, not the Options instance, as the 'to' attribute. Also refactored many-to-one lookup function to be a method of Model.
git-svn-id: http://code.djangoproject.com/svn/django/branches/magic-removal@1600 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
parent
99431aae66
commit
795ac34f3b
|
@ -51,12 +51,12 @@ class RelatedFilterSpec(FilterSpec):
|
||||||
def __init__(self, f, request, params):
|
def __init__(self, f, request, params):
|
||||||
super(RelatedFilterSpec, self).__init__(f, request, params)
|
super(RelatedFilterSpec, self).__init__(f, request, params)
|
||||||
if isinstance(f, meta.ManyToManyField):
|
if isinstance(f, meta.ManyToManyField):
|
||||||
self.lookup_title = f.rel.to.verbose_name
|
self.lookup_title = f.rel.to._meta.verbose_name
|
||||||
else:
|
else:
|
||||||
self.lookup_title = f.verbose_name
|
self.lookup_title = f.verbose_name
|
||||||
self.lookup_kwarg = '%s__%s__exact' % (f.name, f.rel.to.pk.name)
|
self.lookup_kwarg = '%s__%s__exact' % (f.name, f.rel.to._meta.pk.name)
|
||||||
self.lookup_val = request.GET.get(self.lookup_kwarg, None)
|
self.lookup_val = request.GET.get(self.lookup_kwarg, None)
|
||||||
self.lookup_choices = f.rel.to.get_model_module().get_list()
|
self.lookup_choices = f.rel.to._meta.get_model_module().get_list()
|
||||||
|
|
||||||
def has_output(self):
|
def has_output(self):
|
||||||
return len(self.lookup_choices) > 1
|
return len(self.lookup_choices) > 1
|
||||||
|
@ -69,7 +69,7 @@ class RelatedFilterSpec(FilterSpec):
|
||||||
'query_string': cl.get_query_string({}, [self.lookup_kwarg]),
|
'query_string': cl.get_query_string({}, [self.lookup_kwarg]),
|
||||||
'display': _('All')}
|
'display': _('All')}
|
||||||
for val in self.lookup_choices:
|
for val in self.lookup_choices:
|
||||||
pk_val = getattr(val, self.field.rel.to.pk.attname)
|
pk_val = getattr(val, self.field.rel.to._meta.pk.attname)
|
||||||
yield {'selected': self.lookup_val == str(pk_val),
|
yield {'selected': self.lookup_val == str(pk_val),
|
||||||
'query_string': cl.get_query_string( {self.lookup_kwarg: pk_val}),
|
'query_string': cl.get_query_string( {self.lookup_kwarg: pk_val}),
|
||||||
'display': val}
|
'display': val}
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
{% load admin_modify adminmedia %}
|
{% load admin_modify adminmedia %}
|
||||||
{% output_all bound_field.form_fields %}
|
{% output_all bound_field.form_fields %}
|
||||||
{% if bound_field.raw_id_admin %}
|
{% if bound_field.raw_id_admin %}
|
||||||
<a href="../../../{{ bound_field.field.rel.to.app_label }}/{{ bound_field.field.rel.to.module_name }}/" class="related-lookup" id="lookup_{{ bound_field.element_id }}" onclick="return showRelatedObjectLookupPopup(this);"> <img src="{% admin_media_prefix %}img/admin/selector-search.gif" width="16" height="16" alt="Lookup"></a>
|
<a href="../../../{{ bound_field.field.rel.to._meta.app_label }}/{{ bound_field.field.rel.to._meta.module_name }}/" class="related-lookup" id="lookup_{{ bound_field.element_id }}" onclick="return showRelatedObjectLookupPopup(this);"> <img src="{% admin_media_prefix %}img/admin/selector-search.gif" width="16" height="16" alt="Lookup"></a>
|
||||||
{% else %}
|
{% else %}
|
||||||
{% if bound_field.needs_add_label %}
|
{% if bound_field.needs_add_label %}
|
||||||
<a href="../../../{{ bound_field.field.rel.to.app_label }}/{{ bound_field.field.rel.to.module_name }}/add/" class="add-another" id="add_{{ bound_field.element_id }}" onclick="return showAddAnotherPopup(this);"> <img src="{% admin_media_prefix %}img/admin/icon_addlink.gif" width="10" height="10" alt="Add Another"/></a>
|
<a href="../../../{{ bound_field.field.rel.to._meta.app_label }}/{{ bound_field.field.rel.to._meta.module_name }}/add/" class="add-another" id="add_{{ bound_field.element_id }}" onclick="return showAddAnotherPopup(this);"> <img src="{% admin_media_prefix %}img/admin/icon_addlink.gif" width="10" height="10" alt="Add Another"/></a>
|
||||||
{% endif %}{% endif %}
|
{% endif %}{% endif %}
|
||||||
|
|
|
@ -201,8 +201,8 @@ class ChangeList(object):
|
||||||
else:
|
else:
|
||||||
if isinstance(lookup_opts.get_field(order_field).rel, meta.ManyToOne):
|
if isinstance(lookup_opts.get_field(order_field).rel, meta.ManyToOne):
|
||||||
f = lookup_opts.get_field(order_field)
|
f = lookup_opts.get_field(order_field)
|
||||||
rel_ordering = f.rel.to.ordering and f.rel.to.ordering[0] or f.rel.to.pk.column
|
rel_ordering = f.rel.to._meta.ordering and f.rel.to._meta.ordering[0] or f.rel.to._meta.pk.column
|
||||||
lookup_order_field = '%s.%s' % (f.rel.to.db_table, rel_ordering)
|
lookup_order_field = '%s.%s' % (f.rel.to._meta.db_table, rel_ordering)
|
||||||
# Use select_related if one of the list_display options is a field with a
|
# Use select_related if one of the list_display options is a field with a
|
||||||
# relationship.
|
# relationship.
|
||||||
if lookup_opts.admin.list_select_related:
|
if lookup_opts.admin.list_select_related:
|
||||||
|
@ -285,7 +285,7 @@ class AdminBoundField(BoundField):
|
||||||
self.raw_id_admin = use_raw_id_admin(field)
|
self.raw_id_admin = use_raw_id_admin(field)
|
||||||
self.is_date_time = isinstance(field, meta.DateTimeField)
|
self.is_date_time = isinstance(field, meta.DateTimeField)
|
||||||
self.is_file_field = isinstance(field, meta.FileField)
|
self.is_file_field = isinstance(field, meta.FileField)
|
||||||
self.needs_add_label = field.rel and isinstance(field.rel, meta.ManyToOne) or isinstance(field.rel, meta.ManyToMany) and field.rel.to.admin
|
self.needs_add_label = field.rel and isinstance(field.rel, meta.ManyToOne) or isinstance(field.rel, meta.ManyToMany) and field.rel.to._meta.admin
|
||||||
self.hidden = isinstance(self.field, meta.AutoField)
|
self.hidden = isinstance(self.field, meta.AutoField)
|
||||||
self.first = False
|
self.first = False
|
||||||
|
|
||||||
|
@ -525,7 +525,7 @@ def change_stage(request, app_label, module_name, object_id):
|
||||||
#TODO Should be done in flatten_data / FormWrapper construction
|
#TODO Should be done in flatten_data / FormWrapper construction
|
||||||
for related in opts.get_followed_related_objects():
|
for related in opts.get_followed_related_objects():
|
||||||
wrt = related.opts.order_with_respect_to
|
wrt = related.opts.order_with_respect_to
|
||||||
if wrt and wrt.rel and wrt.rel.to == opts:
|
if wrt and wrt.rel and wrt.rel.to._meta == opts:
|
||||||
func = getattr(manipulator.original_object, 'get_%s_list' %
|
func = getattr(manipulator.original_object, 'get_%s_list' %
|
||||||
related.get_method_name_part())
|
related.get_method_name_part())
|
||||||
orig_list = func()
|
orig_list = func()
|
||||||
|
|
|
@ -82,8 +82,8 @@ def get_sql_create(mod):
|
||||||
field_output.append('PRIMARY KEY')
|
field_output.append('PRIMARY KEY')
|
||||||
if f.rel:
|
if f.rel:
|
||||||
field_output.append('REFERENCES %s (%s)' % \
|
field_output.append('REFERENCES %s (%s)' % \
|
||||||
(db.db.quote_name(f.rel.to.db_table),
|
(db.db.quote_name(f.rel.to._meta.db_table),
|
||||||
db.db.quote_name(f.rel.to.get_field(f.rel.field_name).column)))
|
db.db.quote_name(f.rel.to._meta.get_field(f.rel.field_name).column)))
|
||||||
table_output.append(' '.join(field_output))
|
table_output.append(' '.join(field_output))
|
||||||
if opts.order_with_respect_to:
|
if opts.order_with_respect_to:
|
||||||
table_output.append('%s %s NULL' % (db.db.quote_name('_order'), db.DATA_TYPES['IntegerField']))
|
table_output.append('%s %s NULL' % (db.db.quote_name('_order'), db.DATA_TYPES['IntegerField']))
|
||||||
|
@ -108,13 +108,13 @@ def get_sql_create(mod):
|
||||||
db.db.quote_name(opts.db_table),
|
db.db.quote_name(opts.db_table),
|
||||||
db.db.quote_name(opts.pk.column)))
|
db.db.quote_name(opts.pk.column)))
|
||||||
table_output.append(' %s %s NOT NULL REFERENCES %s (%s),' % \
|
table_output.append(' %s %s NOT NULL REFERENCES %s (%s),' % \
|
||||||
(db.db.quote_name(f.rel.to.object_name.lower() + '_id'),
|
(db.db.quote_name(f.rel.to._meta.object_name.lower() + '_id'),
|
||||||
db.DATA_TYPES[get_rel_data_type(f.rel.to.pk)] % f.rel.to.pk.__dict__,
|
db.DATA_TYPES[get_rel_data_type(f.rel.to._meta.pk)] % f.rel.to._meta.pk.__dict__,
|
||||||
db.db.quote_name(f.rel.to.db_table),
|
db.db.quote_name(f.rel.to._meta.db_table),
|
||||||
db.db.quote_name(f.rel.to.pk.column)))
|
db.db.quote_name(f.rel.to._meta.pk.column)))
|
||||||
table_output.append(' UNIQUE (%s, %s)' % \
|
table_output.append(' UNIQUE (%s, %s)' % \
|
||||||
(db.db.quote_name(opts.object_name.lower() + '_id'),
|
(db.db.quote_name(opts.object_name.lower() + '_id'),
|
||||||
db.db.quote_name(f.rel.to.object_name.lower() + '_id')))
|
db.db.quote_name(f.rel.to._meta.object_name.lower() + '_id')))
|
||||||
table_output.append(');')
|
table_output.append(');')
|
||||||
final_output.append('\n'.join(table_output))
|
final_output.append('\n'.join(table_output))
|
||||||
return final_output
|
return final_output
|
||||||
|
@ -669,8 +669,8 @@ def get_validation_errors(outfile):
|
||||||
# verify "singular" is set in that case.
|
# verify "singular" is set in that case.
|
||||||
for i, f in enumerate(opts.many_to_many):
|
for i, f in enumerate(opts.many_to_many):
|
||||||
for previous_f in opts.many_to_many[:i]:
|
for previous_f in opts.many_to_many[:i]:
|
||||||
if f.rel.to == previous_f.rel.to and f.rel.singular == previous_f.rel.singular:
|
if f.rel.to._meta == previous_f.rel.to._meta and f.rel.singular == previous_f.rel.singular:
|
||||||
e.add(opts, 'The "%s" field requires a "singular" parameter, because the %s model has more than one ManyToManyField to the same model (%s).' % (f.name, opts.object_name, previous_f.rel.to.object_name))
|
e.add(opts, 'The "%s" field requires a "singular" parameter, because the %s model has more than one ManyToManyField to the same model (%s).' % (f.name, opts.object_name, previous_f.rel.to._meta.object_name))
|
||||||
|
|
||||||
# Check admin attribute.
|
# Check admin attribute.
|
||||||
if opts.admin is not None:
|
if opts.admin is not None:
|
||||||
|
|
|
@ -486,7 +486,7 @@ class Options:
|
||||||
for mod in module_list:
|
for mod in module_list:
|
||||||
for klass in mod._MODELS:
|
for klass in mod._MODELS:
|
||||||
for f in klass._meta.fields:
|
for f in klass._meta.fields:
|
||||||
if f.rel and self == f.rel.to:
|
if f.rel and self == f.rel.to._meta:
|
||||||
rel_objs.append(RelatedObject(self, klass._meta, f))
|
rel_objs.append(RelatedObject(self, klass._meta, f))
|
||||||
if self.has_related_links:
|
if self.has_related_links:
|
||||||
# Manually add RelatedLink objects, which are a special case.
|
# Manually add RelatedLink objects, which are a special case.
|
||||||
|
@ -533,7 +533,7 @@ class Options:
|
||||||
for mod in module_list:
|
for mod in module_list:
|
||||||
for klass in mod._MODELS:
|
for klass in mod._MODELS:
|
||||||
for f in klass._meta.many_to_many:
|
for f in klass._meta.many_to_many:
|
||||||
if f.rel and self == f.rel.to:
|
if f.rel and self == f.rel.to._meta:
|
||||||
rel_objs.append(RelatedObject(self, klass._meta, f))
|
rel_objs.append(RelatedObject(self, klass._meta, f))
|
||||||
return rel_objs
|
return rel_objs
|
||||||
|
|
||||||
|
@ -544,7 +544,7 @@ class Options:
|
||||||
for klass in get_app(self.app_label)._MODELS:
|
for klass in get_app(self.app_label)._MODELS:
|
||||||
opts = klass._meta
|
opts = klass._meta
|
||||||
if opts.order_with_respect_to and opts.order_with_respect_to.rel \
|
if opts.order_with_respect_to and opts.order_with_respect_to.rel \
|
||||||
and self == opts.order_with_respect_to.rel.to:
|
and self == opts.order_with_respect_to.rel.to._meta:
|
||||||
objects.append(opts)
|
objects.append(opts)
|
||||||
self._ordered_objects = objects
|
self._ordered_objects = objects
|
||||||
return self._ordered_objects
|
return self._ordered_objects
|
||||||
|
@ -722,31 +722,16 @@ class ModelBase(type):
|
||||||
setattr(new_mod, k, v)
|
setattr(new_mod, k, v)
|
||||||
|
|
||||||
# Create the default class methods.
|
# Create the default class methods.
|
||||||
for f in opts.fields:
|
|
||||||
# If the object has a relationship to itself, as designated by
|
|
||||||
# RECURSIVE_RELATIONSHIP_CONSTANT, create that relationship formally.
|
|
||||||
if f.rel and f.rel.to == RECURSIVE_RELATIONSHIP_CONSTANT:
|
|
||||||
f.rel.to = opts
|
|
||||||
f.name = f.name or (f.rel.to.object_name.lower() + '_' + f.rel.to.pk.name)
|
|
||||||
f.verbose_name = f.verbose_name or f.rel.to.verbose_name
|
|
||||||
f.rel.field_name = f.rel.field_name or f.rel.to.pk.name
|
|
||||||
# Add "get_thingie" methods for many-to-one related objects.
|
|
||||||
# EXAMPLES: Choice.get_poll(), Story.get_dateline()
|
|
||||||
if isinstance(f.rel, ManyToOne):
|
|
||||||
func = curry(method_get_many_to_one, f)
|
|
||||||
func.__doc__ = "Returns the associated `%s.%s` object." % (f.rel.to.app_label, f.rel.to.module_name)
|
|
||||||
attrs['get_%s' % f.name] = func
|
|
||||||
|
|
||||||
for f in opts.many_to_many:
|
for f in opts.many_to_many:
|
||||||
# Add "get_thingie" methods for many-to-many related objects.
|
# Add "get_thingie" methods for many-to-many related objects.
|
||||||
# EXAMPLES: Poll.get_site_list(), Story.get_byline_list()
|
# EXAMPLES: Poll.get_site_list(), Story.get_byline_list()
|
||||||
func = curry(method_get_many_to_many, f)
|
func = curry(method_get_many_to_many, f)
|
||||||
func.__doc__ = "Returns a list of associated `%s.%s` objects." % (f.rel.to.app_label, f.rel.to.module_name)
|
func.__doc__ = "Returns a list of associated `%s.%s` objects." % (f.rel.to._meta.app_label, f.rel.to._meta.module_name)
|
||||||
attrs['get_%s_list' % f.rel.singular] = func
|
attrs['get_%s_list' % f.rel.singular] = func
|
||||||
# Add "set_thingie" methods for many-to-many related objects.
|
# Add "set_thingie" methods for many-to-many related objects.
|
||||||
# EXAMPLES: Poll.set_sites(), Story.set_bylines()
|
# EXAMPLES: Poll.set_sites(), Story.set_bylines()
|
||||||
func = curry(method_set_many_to_many, f)
|
func = curry(method_set_many_to_many, f)
|
||||||
func.__doc__ = "Resets this object's `%s.%s` list to the given list of IDs. Note that it doesn't check whether the given IDs are valid." % (f.rel.to.app_label, f.rel.to.module_name)
|
func.__doc__ = "Resets this object's `%s.%s` list to the given list of IDs. Note that it doesn't check whether the given IDs are valid." % (f.rel.to._meta.app_label, f.rel.to._meta.module_name)
|
||||||
func.alters_data = True
|
func.alters_data = True
|
||||||
attrs['set_%s' % f.name] = func
|
attrs['set_%s' % f.name] = func
|
||||||
|
|
||||||
|
@ -915,21 +900,35 @@ class Model:
|
||||||
setattr(cls, 'get_next_by_%s' % f.name, curry(cls.__get_next_or_previous_by_FIELD, field=f, is_next=True))
|
setattr(cls, 'get_next_by_%s' % f.name, curry(cls.__get_next_or_previous_by_FIELD, field=f, is_next=True))
|
||||||
setattr(cls, 'get_previous_by_%s' % f.name, curry(cls.__get_next_or_previous_by_FIELD, field=f, is_next=False))
|
setattr(cls, 'get_previous_by_%s' % f.name, curry(cls.__get_next_or_previous_by_FIELD, field=f, is_next=False))
|
||||||
elif isinstance(f, FileField):
|
elif isinstance(f, FileField):
|
||||||
setattr(cls, 'get_%s_filename' % f.name, curry(cls.__get_FIELD_filename, f))
|
setattr(cls, 'get_%s_filename' % f.name, curry(cls.__get_FIELD_filename, field=f))
|
||||||
setattr(cls, 'get_%s_url' % f.name, curry(cls.__get_FIELD_url, f))
|
setattr(cls, 'get_%s_url' % f.name, curry(cls.__get_FIELD_url, field=f))
|
||||||
setattr(cls, 'get_%s_size' % f.name, curry(cls.__get_FIELD_size, f))
|
setattr(cls, 'get_%s_size' % f.name, curry(cls.__get_FIELD_size, field=f))
|
||||||
setattr(cls, 'save_%s_file' % f.name, curry(cls.__save_FIELD_file, f))
|
setattr(cls, 'save_%s_file' % f.name, curry(cls.__save_FIELD_file, field=f))
|
||||||
if isinstance(f, ImageField):
|
if isinstance(f, ImageField):
|
||||||
# Add get_BLAH_width and get_BLAH_height methods, but only
|
# Add get_BLAH_width and get_BLAH_height methods, but only
|
||||||
# if the image field doesn't have width and height cache
|
# if the image field doesn't have width and height cache
|
||||||
# fields.
|
# fields.
|
||||||
if not f.width_field:
|
if not f.width_field:
|
||||||
setattr(cls, 'get_%s_width' % f.name, curry(cls.__get_FIELD_width, f))
|
setattr(cls, 'get_%s_width' % f.name, curry(cls.__get_FIELD_width, field=f))
|
||||||
if not f.height_field:
|
if not f.height_field:
|
||||||
setattr(cls, 'get_%s_height' % f.name, curry(cls.__get_FIELD_height, f))
|
setattr(cls, 'get_%s_height' % f.name, curry(cls.__get_FIELD_height, field=f))
|
||||||
|
|
||||||
|
# If the object has a relationship to itself, as designated by
|
||||||
|
# RECURSIVE_RELATIONSHIP_CONSTANT, create that relationship formally.
|
||||||
|
if f.rel and f.rel.to == RECURSIVE_RELATIONSHIP_CONSTANT:
|
||||||
|
f.rel.to = cls
|
||||||
|
f.name = f.name or (f.rel.to._meta.object_name.lower() + '_' + f.rel.to._meta.pk.name)
|
||||||
|
f.verbose_name = f.verbose_name or f.rel.to._meta.verbose_name
|
||||||
|
f.rel.field_name = f.rel.field_name or f.rel.to._meta.pk.name
|
||||||
|
|
||||||
|
# Add methods for many-to-one related objects.
|
||||||
|
# EXAMPLES: Choice.get_poll(), Story.get_dateline()
|
||||||
|
if isinstance(f.rel, ManyToOne):
|
||||||
|
setattr(cls, 'get_%s' % f.name, curry(cls.__get_foreign_key_object, field_with_rel=f))
|
||||||
|
|
||||||
if cls._meta.order_with_respect_to:
|
if cls._meta.order_with_respect_to:
|
||||||
cls.get_next_in_order = curry(cls.__get_next_or_previous_in_order, True)
|
cls.get_next_in_order = curry(cls.__get_next_or_previous_in_order, is_next=True)
|
||||||
cls.get_previous_in_order = curry(cls.__get_next_or_previous_in_order, False)
|
cls.get_previous_in_order = curry(cls.__get_next_or_previous_in_order, is_next=False)
|
||||||
|
|
||||||
_prepare = classmethod(_prepare)
|
_prepare = classmethod(_prepare)
|
||||||
|
|
||||||
|
@ -1130,6 +1129,21 @@ class Model:
|
||||||
setattr(self, cachename, get_image_dimensions(filename))
|
setattr(self, cachename, get_image_dimensions(filename))
|
||||||
return getattr(self, cachename)
|
return getattr(self, cachename)
|
||||||
|
|
||||||
|
def __get_foreign_key_object(self, field_with_rel):
|
||||||
|
cache_var = field_with_rel.get_cache_name()
|
||||||
|
if not hasattr(self, cache_var):
|
||||||
|
val = getattr(self, field_with_rel.attname)
|
||||||
|
if val is None:
|
||||||
|
raise field_with_rel.rel.to.DoesNotExist
|
||||||
|
other_field = field_with_rel.rel.get_related_field()
|
||||||
|
if other_field.rel:
|
||||||
|
params = {'%s__%s__exact' % (field_with_rel.rel.field_name, other_field.rel.field_name): val}
|
||||||
|
else:
|
||||||
|
params = {'%s__exact' % field_with_rel.rel.field_name: val}
|
||||||
|
retrieved_obj = field_with_rel.rel.to.objects.get_object(**params)
|
||||||
|
setattr(self, cache_var, retrieved_obj)
|
||||||
|
return getattr(self, cache_var)
|
||||||
|
|
||||||
class Manager:
|
class Manager:
|
||||||
def __init__(self, model_class):
|
def __init__(self, model_class):
|
||||||
self.klass = model_class
|
self.klass = model_class
|
||||||
|
@ -1320,23 +1334,6 @@ class Manager:
|
||||||
|
|
||||||
# RELATIONSHIP METHODS #####################
|
# RELATIONSHIP METHODS #####################
|
||||||
|
|
||||||
# Example: Story.get_dateline()
|
|
||||||
def method_get_many_to_one(field_with_rel, self):
|
|
||||||
cache_var = field_with_rel.get_cache_name()
|
|
||||||
if not hasattr(self, cache_var):
|
|
||||||
val = getattr(self, field_with_rel.attname)
|
|
||||||
mod = field_with_rel.rel.to.get_model_module()
|
|
||||||
if val is None:
|
|
||||||
raise getattr(mod, '%sDoesNotExist' % field_with_rel.rel.to.object_name)
|
|
||||||
other_field = field_with_rel.rel.get_related_field()
|
|
||||||
if other_field.rel:
|
|
||||||
params = {'%s__%s__exact' % (field_with_rel.rel.field_name, other_field.rel.field_name): val}
|
|
||||||
else:
|
|
||||||
params = {'%s__exact'% field_with_rel.rel.field_name: val}
|
|
||||||
retrieved_obj = mod.get_object(**params)
|
|
||||||
setattr(self, cache_var, retrieved_obj)
|
|
||||||
return getattr(self, cache_var)
|
|
||||||
|
|
||||||
# Handles getting many-to-many related objects.
|
# Handles getting many-to-many related objects.
|
||||||
# Example: Poll.get_site_list()
|
# Example: Poll.get_site_list()
|
||||||
def method_get_many_to_many(field_with_rel, self):
|
def method_get_many_to_many(field_with_rel, self):
|
||||||
|
@ -1399,7 +1396,7 @@ def method_get_related(method_name, rel_mod, rel_field, self, **kwargs):
|
||||||
if self._meta.has_related_links and rel_mod.Klass._meta.module_name == 'relatedlinks':
|
if self._meta.has_related_links and rel_mod.Klass._meta.module_name == 'relatedlinks':
|
||||||
kwargs['object_id__exact'] = getattr(self, rel_field.rel.field_name)
|
kwargs['object_id__exact'] = getattr(self, rel_field.rel.field_name)
|
||||||
else:
|
else:
|
||||||
kwargs['%s__%s__exact' % (rel_field.name, rel_field.rel.to.pk.name)] = getattr(self, rel_field.rel.get_related_field().attname)
|
kwargs['%s__%s__exact' % (rel_field.name, rel_field.rel.to._meta.pk.name)] = getattr(self, rel_field.rel.get_related_field().attname)
|
||||||
kwargs.update(rel_field.rel.lookup_overrides)
|
kwargs.update(rel_field.rel.lookup_overrides)
|
||||||
return getattr(rel_mod, method_name)(**kwargs)
|
return getattr(rel_mod, method_name)(**kwargs)
|
||||||
|
|
||||||
|
@ -1507,7 +1504,7 @@ def _fill_table_cache(opts, select, tables, where, old_prefix, cache_tables_seen
|
||||||
"""
|
"""
|
||||||
for f in opts.fields:
|
for f in opts.fields:
|
||||||
if f.rel and not f.null:
|
if f.rel and not f.null:
|
||||||
db_table = f.rel.to.db_table
|
db_table = f.rel.to._meta.db_table
|
||||||
if db_table not in cache_tables_seen:
|
if db_table not in cache_tables_seen:
|
||||||
tables.append(db.db.quote_name(db_table))
|
tables.append(db.db.quote_name(db_table))
|
||||||
else: # The table was already seen, so give it a table alias.
|
else: # The table was already seen, so give it a table alias.
|
||||||
|
@ -1518,7 +1515,7 @@ def _fill_table_cache(opts, select, tables, where, old_prefix, cache_tables_seen
|
||||||
where.append('%s.%s = %s.%s' % \
|
where.append('%s.%s = %s.%s' % \
|
||||||
(db.db.quote_name(old_prefix), db.db.quote_name(f.column),
|
(db.db.quote_name(old_prefix), db.db.quote_name(f.column),
|
||||||
db.db.quote_name(db_table), db.db.quote_name(f.rel.get_related_field().column)))
|
db.db.quote_name(db_table), db.db.quote_name(f.rel.get_related_field().column)))
|
||||||
select.extend(['%s.%s' % (db.db.quote_name(db_table), db.db.quote_name(f2.column)) for f2 in f.rel.to.fields])
|
select.extend(['%s.%s' % (db.db.quote_name(db_table), db.db.quote_name(f2.column)) for f2 in f.rel.to._meta.fields])
|
||||||
_fill_table_cache(f.rel.to, select, tables, where, db_table, cache_tables_seen)
|
_fill_table_cache(f.rel.to, select, tables, where, db_table, cache_tables_seen)
|
||||||
|
|
||||||
def _throw_bad_kwarg_error(kwarg):
|
def _throw_bad_kwarg_error(kwarg):
|
||||||
|
@ -1595,31 +1592,31 @@ def _parse_lookup(kwarg_items, opts, table_count=0):
|
||||||
db.db.quote_name(current_opts.object_name.lower() + '_id')))
|
db.db.quote_name(current_opts.object_name.lower() + '_id')))
|
||||||
# Optimization: In the case of primary-key lookups, we
|
# Optimization: In the case of primary-key lookups, we
|
||||||
# don't have to do an extra join.
|
# don't have to do an extra join.
|
||||||
if lookup_list and lookup_list[0] == f.rel.to.pk.name and lookup_type == 'exact':
|
if lookup_list and lookup_list[0] == f.rel.to._meta.pk.name and lookup_type == 'exact':
|
||||||
where.append(_get_where_clause(lookup_type, rel_table_alias+'.',
|
where.append(_get_where_clause(lookup_type, rel_table_alias+'.',
|
||||||
f.rel.to.object_name.lower()+'_id', kwarg_value))
|
f.rel.to._meta.object_name.lower()+'_id', kwarg_value))
|
||||||
params.extend(f.get_db_prep_lookup(lookup_type, kwarg_value))
|
params.extend(f.get_db_prep_lookup(lookup_type, kwarg_value))
|
||||||
lookup_list.pop()
|
lookup_list.pop()
|
||||||
param_required = False
|
param_required = False
|
||||||
else:
|
else:
|
||||||
new_table_alias = 't%s' % table_count
|
new_table_alias = 't%s' % table_count
|
||||||
tables.append('%s %s' % (db.db.quote_name(f.rel.to.db_table),
|
tables.append('%s %s' % (db.db.quote_name(f.rel.to._meta.db_table),
|
||||||
db.db.quote_name(new_table_alias)))
|
db.db.quote_name(new_table_alias)))
|
||||||
join_where.append('%s.%s = %s.%s' % \
|
join_where.append('%s.%s = %s.%s' % \
|
||||||
(db.db.quote_name(rel_table_alias),
|
(db.db.quote_name(rel_table_alias),
|
||||||
db.db.quote_name(f.rel.to.object_name.lower() + '_id'),
|
db.db.quote_name(f.rel.to._meta.object_name.lower() + '_id'),
|
||||||
db.db.quote_name(new_table_alias),
|
db.db.quote_name(new_table_alias),
|
||||||
db.db.quote_name(f.rel.to.pk.column)))
|
db.db.quote_name(f.rel.to._meta.pk.column)))
|
||||||
current_table_alias = new_table_alias
|
current_table_alias = new_table_alias
|
||||||
param_required = True
|
param_required = True
|
||||||
current_opts = f.rel.to
|
current_opts = f.rel.to._meta
|
||||||
raise StopIteration
|
raise StopIteration
|
||||||
for f in current_opts.fields:
|
for f in current_opts.fields:
|
||||||
# Try many-to-one relationships...
|
# Try many-to-one relationships...
|
||||||
if f.rel and f.name == current:
|
if f.rel and f.name == current:
|
||||||
# Optimization: In the case of primary-key lookups, we
|
# Optimization: In the case of primary-key lookups, we
|
||||||
# don't have to do an extra join.
|
# don't have to do an extra join.
|
||||||
if lookup_list and lookup_list[0] == f.rel.to.pk.name and lookup_type == 'exact':
|
if lookup_list and lookup_list[0] == f.rel.to._meta.pk.name and lookup_type == 'exact':
|
||||||
where.append(_get_where_clause(lookup_type, current_table_alias+'.', f.column, kwarg_value))
|
where.append(_get_where_clause(lookup_type, current_table_alias+'.', f.column, kwarg_value))
|
||||||
params.extend(f.get_db_prep_lookup(lookup_type, kwarg_value))
|
params.extend(f.get_db_prep_lookup(lookup_type, kwarg_value))
|
||||||
lookup_list.pop()
|
lookup_list.pop()
|
||||||
|
@ -1633,13 +1630,13 @@ def _parse_lookup(kwarg_items, opts, table_count=0):
|
||||||
else:
|
else:
|
||||||
new_table_alias = 't%s' % table_count
|
new_table_alias = 't%s' % table_count
|
||||||
tables.append('%s %s' % \
|
tables.append('%s %s' % \
|
||||||
(db.db.quote_name(f.rel.to.db_table), db.db.quote_name(new_table_alias)))
|
(db.db.quote_name(f.rel.to._meta.db_table), db.db.quote_name(new_table_alias)))
|
||||||
join_where.append('%s.%s = %s.%s' % \
|
join_where.append('%s.%s = %s.%s' % \
|
||||||
(db.db.quote_name(current_table_alias), db.db.quote_name(f.column),
|
(db.db.quote_name(current_table_alias), db.db.quote_name(f.column),
|
||||||
db.db.quote_name(new_table_alias), db.db.quote_name(f.rel.to.pk.column)))
|
db.db.quote_name(new_table_alias), db.db.quote_name(f.rel.to._meta.pk.column)))
|
||||||
current_table_alias = new_table_alias
|
current_table_alias = new_table_alias
|
||||||
param_required = True
|
param_required = True
|
||||||
current_opts = f.rel.to
|
current_opts = f.rel.to._meta
|
||||||
raise StopIteration
|
raise StopIteration
|
||||||
# Try direct field-name lookups...
|
# Try direct field-name lookups...
|
||||||
if f.name == current:
|
if f.name == current:
|
||||||
|
@ -1699,7 +1696,7 @@ def manipulator_init(opts, add, change, self, obj_key=None, follow=None):
|
||||||
# Let the ObjectDoesNotExist exception propogate up.
|
# Let the ObjectDoesNotExist exception propogate up.
|
||||||
lookup_kwargs = opts.one_to_one_field.rel.limit_choices_to
|
lookup_kwargs = opts.one_to_one_field.rel.limit_choices_to
|
||||||
lookup_kwargs['%s__exact' % opts.one_to_one_field.rel.field_name] = obj_key
|
lookup_kwargs['%s__exact' % opts.one_to_one_field.rel.field_name] = obj_key
|
||||||
_ = opts.one_to_one_field.rel.to.get_model_module().get_object(**lookup_kwargs)
|
_ = opts.one_to_one_field.rel.to._meta.get_model_module().get_object(**lookup_kwargs)
|
||||||
params = dict([(f.attname, f.get_default()) for f in opts.fields])
|
params = dict([(f.attname, f.get_default()) for f in opts.fields])
|
||||||
params[opts.pk.attname] = obj_key
|
params[opts.pk.attname] = obj_key
|
||||||
self.original_object = opts.get_model_module().Klass(**params)
|
self.original_object = opts.get_model_module().Klass(**params)
|
||||||
|
|
|
@ -39,7 +39,7 @@ string_concat = lazy(string_concat, str)
|
||||||
|
|
||||||
def manipulator_valid_rel_key(f, self, field_data, all_data):
|
def manipulator_valid_rel_key(f, self, field_data, all_data):
|
||||||
"Validates that the value is a valid foreign key"
|
"Validates that the value is a valid foreign key"
|
||||||
mod = f.rel.to.get_model_module()
|
mod = f.rel.to._meta.get_model_module()
|
||||||
try:
|
try:
|
||||||
mod.get_object(pk=field_data)
|
mod.get_object(pk=field_data)
|
||||||
except ObjectDoesNotExist:
|
except ObjectDoesNotExist:
|
||||||
|
@ -311,9 +311,9 @@ class Field(object):
|
||||||
first_choice = include_blank and blank_choice or []
|
first_choice = include_blank and blank_choice or []
|
||||||
if self.choices:
|
if self.choices:
|
||||||
return first_choice + list(self.choices)
|
return first_choice + list(self.choices)
|
||||||
rel_obj = self.rel.to
|
rel_model = self.rel.to
|
||||||
return first_choice + [(getattr(x, rel_obj.pk.attname), str(x))
|
return first_choice + [(getattr(x, rel_model._meta.pk.attname), str(x))
|
||||||
for x in rel_obj.get_model_module().get_list(**self.rel.limit_choices_to)]
|
for x in rel_model.objects.get_list(**self.rel._meta.limit_choices_to)]
|
||||||
|
|
||||||
def get_choices_default(self):
|
def get_choices_default(self):
|
||||||
if(self.radio_admin):
|
if(self.radio_admin):
|
||||||
|
@ -770,7 +770,7 @@ class ManyToManyField(Field):
|
||||||
|
|
||||||
def isValidIDList(self, field_data, all_data):
|
def isValidIDList(self, field_data, all_data):
|
||||||
"Validates that the value is a valid list of foreign keys"
|
"Validates that the value is a valid list of foreign keys"
|
||||||
mod = self.rel.to.get_model_module()
|
mod = self.rel.to._meta.get_model_module()
|
||||||
try:
|
try:
|
||||||
pks = map(int, field_data.split(','))
|
pks = map(int, field_data.split(','))
|
||||||
except ValueError:
|
except ValueError:
|
||||||
|
@ -789,7 +789,7 @@ class ManyToManyField(Field):
|
||||||
new_data = {}
|
new_data = {}
|
||||||
if obj:
|
if obj:
|
||||||
get_list_func = getattr(obj, 'get_%s_list' % self.rel.singular)
|
get_list_func = getattr(obj, 'get_%s_list' % self.rel.singular)
|
||||||
instance_ids = [getattr(instance, self.rel.to.pk.attname) for instance in get_list_func()]
|
instance_ids = [getattr(instance, self.rel.to._meta.pk.attname) for instance in get_list_func()]
|
||||||
if self.rel.raw_id_admin:
|
if self.rel.raw_id_admin:
|
||||||
new_data[self.name] = ",".join([str(id) for id in instance_ids])
|
new_data[self.name] = ",".join([str(id) for id in instance_ids])
|
||||||
else:
|
else:
|
||||||
|
@ -829,11 +829,10 @@ class ManyToOne:
|
||||||
max_num_in_admin=None, num_extra_on_change=1, edit_inline=False,
|
max_num_in_admin=None, num_extra_on_change=1, edit_inline=False,
|
||||||
related_name=None, limit_choices_to=None, lookup_overrides=None, raw_id_admin=False):
|
related_name=None, limit_choices_to=None, lookup_overrides=None, raw_id_admin=False):
|
||||||
try:
|
try:
|
||||||
self.to = to._meta
|
to._meta
|
||||||
except AttributeError: # to._meta doesn't exist, so it must be RECURSIVE_RELATIONSHIP_CONSTANT
|
except AttributeError: # to._meta doesn't exist, so it must be RECURSIVE_RELATIONSHIP_CONSTANT
|
||||||
assert to == RECURSIVE_RELATIONSHIP_CONSTANT, "'to' must be either a model or the string '%s'" % RECURSIVE_RELATIONSHIP_CONSTANT
|
assert to == RECURSIVE_RELATIONSHIP_CONSTANT, "'to' must be either a model or the string %r" % RECURSIVE_RELATIONSHIP_CONSTANT
|
||||||
self.to = to
|
self.to, self.field_name = to, field_name
|
||||||
self.field_name = field_name
|
|
||||||
self.num_in_admin, self.edit_inline = num_in_admin, edit_inline
|
self.num_in_admin, self.edit_inline = num_in_admin, edit_inline
|
||||||
self.min_num_in_admin, self.max_num_in_admin = min_num_in_admin, max_num_in_admin
|
self.min_num_in_admin, self.max_num_in_admin = min_num_in_admin, max_num_in_admin
|
||||||
self.num_extra_on_change, self.related_name = num_extra_on_change, related_name
|
self.num_extra_on_change, self.related_name = num_extra_on_change, related_name
|
||||||
|
@ -843,12 +842,12 @@ class ManyToOne:
|
||||||
|
|
||||||
def get_related_field(self):
|
def get_related_field(self):
|
||||||
"Returns the Field in the 'to' object to which this relationship is tied."
|
"Returns the Field in the 'to' object to which this relationship is tied."
|
||||||
return self.to.get_field(self.field_name)
|
return self.to._meta.get_field(self.field_name)
|
||||||
|
|
||||||
class ManyToMany:
|
class ManyToMany:
|
||||||
def __init__(self, to, singular=None, num_in_admin=0, related_name=None,
|
def __init__(self, to, singular=None, num_in_admin=0, related_name=None,
|
||||||
filter_interface=None, limit_choices_to=None, raw_id_admin=False):
|
filter_interface=None, limit_choices_to=None, raw_id_admin=False):
|
||||||
self.to = to._meta
|
self.to = to
|
||||||
self.singular = singular or to._meta.object_name.lower()
|
self.singular = singular or to._meta.object_name.lower()
|
||||||
self.num_in_admin = num_in_admin
|
self.num_in_admin = num_in_admin
|
||||||
self.related_name = related_name
|
self.related_name = related_name
|
||||||
|
@ -862,7 +861,7 @@ class OneToOne(ManyToOne):
|
||||||
def __init__(self, to, field_name, num_in_admin=0, edit_inline=False,
|
def __init__(self, to, field_name, num_in_admin=0, edit_inline=False,
|
||||||
related_name=None, limit_choices_to=None, lookup_overrides=None,
|
related_name=None, limit_choices_to=None, lookup_overrides=None,
|
||||||
raw_id_admin=False):
|
raw_id_admin=False):
|
||||||
self.to, self.field_name = to._meta, field_name
|
self.to, self.field_name = to, field_name
|
||||||
self.num_in_admin, self.edit_inline = num_in_admin, edit_inline
|
self.num_in_admin, self.edit_inline = num_in_admin, edit_inline
|
||||||
self.related_name = related_name
|
self.related_name = related_name
|
||||||
self.limit_choices_to = limit_choices_to or {}
|
self.limit_choices_to = limit_choices_to or {}
|
||||||
|
|
Loading…
Reference in New Issue