From 5b47d3b42aa8a5851839f26c003cc1bfdf6539be Mon Sep 17 00:00:00 2001 From: Adrian Holovaty Date: Mon, 29 Jan 2007 16:12:36 +0000 Subject: [PATCH] newforms-admin: Merged to [4449] git-svn-id: http://code.djangoproject.com/svn/django/branches/newforms-admin@4450 bcc190cf-cafb-0310-a4f2-bffc1f526a37 --- django/db/models/fields/related.py | 18 +++++++++++------- django/newforms/models.py | 2 +- docs/design_philosophies.txt | 2 +- tests/modeltests/many_to_many/models.py | 14 +++++++++++++- 4 files changed, 26 insertions(+), 10 deletions(-) diff --git a/django/db/models/fields/related.py b/django/db/models/fields/related.py index ba790a954b..769ac2d9f0 100644 --- a/django/db/models/fields/related.py +++ b/django/db/models/fields/related.py @@ -316,18 +316,20 @@ def create_many_related_manager(superclass): # join_table: name of the m2m link table # source_col_name: the PK colname in join_table for the source object # target_col_name: the PK colname in join_table for the target object - # *objs - objects to add + # *objs - objects to add. Either object instances, or primary keys of object instances. from django.db import connection # If there aren't any objects, there is nothing to do. if objs: # Check that all the objects are of the right type + new_ids = set() for obj in objs: - if not isinstance(obj, self.model): - raise ValueError, "objects to add() must be %s instances" % self.model._meta.object_name + if isinstance(obj, self.model): + new_ids.add(obj._get_pk_val()) + else: + new_ids.add(obj) # Add the newly created or already existing objects to the join table. # First find out which items are already added, to avoid adding them twice - new_ids = set([obj._get_pk_val() for obj in objs]) cursor = connection.cursor() cursor.execute("SELECT %s FROM %s WHERE %s = %%s AND %s IN (%s)" % \ (target_col_name, self.join_table, source_col_name, @@ -354,11 +356,13 @@ def create_many_related_manager(superclass): # If there aren't any objects, there is nothing to do. if objs: # Check that all the objects are of the right type + old_ids = set() for obj in objs: - if not isinstance(obj, self.model): - raise ValueError, "objects to remove() must be %s instances" % self.model._meta.object_name + if isinstance(obj, self.model): + old_ids.add(obj._get_pk_val()) + else: + old_ids.add(obj) # Remove the specified objects from the join table - old_ids = set([obj._get_pk_val() for obj in objs]) cursor = connection.cursor() cursor.execute("DELETE FROM %s WHERE %s = %%s AND %s IN (%s)" % \ (self.join_table, source_col_name, diff --git a/django/newforms/models.py b/django/newforms/models.py index 9bd6a3ff83..a938b6350e 100644 --- a/django/newforms/models.py +++ b/django/newforms/models.py @@ -37,7 +37,7 @@ def save_instance(form, instance, commit=True): if commit: instance.save() for f in opts.many_to_many: - setattr(instance, f.attname, getattr(instance, f.attname).model.objects.filter(pk__in = clean_data[f.name])) + setattr(instance, f.attname, clean_data[f.name]) # GOTCHA: If many-to-many data is given and commit=False, the many-to-many # data will be lost. This happens because a many-to-many options cannot be # set on an object until after it's saved. Maybe we should raise an diff --git a/docs/design_philosophies.txt b/docs/design_philosophies.txt index b2733640e9..72aa8ade95 100644 --- a/docs/design_philosophies.txt +++ b/docs/design_philosophies.txt @@ -186,7 +186,7 @@ code. This is the philosophy behind `template inheritance`_. -.. _template inheritance: ./templates/#template-inheritance +.. _template inheritance: ../templates/#template-inheritance Be decoupled from HTML ---------------------- diff --git a/tests/modeltests/many_to_many/models.py b/tests/modeltests/many_to_many/models.py index 38f8931ee7..5e46ad428d 100644 --- a/tests/modeltests/many_to_many/models.py +++ b/tests/modeltests/many_to_many/models.py @@ -203,7 +203,19 @@ __test__ = {'API_TESTS':""" >>> p2.article_set.all() [] -# Recreate the article and Publication we just deleted. +# Relation sets can also be set using primary key values +>>> p2.article_set = [a4.id, a5.id] +>>> p2.article_set.all() +[, ] +>>> a4.publications.all() +[] +>>> a4.publications = [p3.id] +>>> p2.article_set.all() +[] +>>> a4.publications.all() +[] + +# Recreate the article and Publication we have deleted. >>> p1 = Publication(id=None, title='The Python Journal') >>> p1.save() >>> a2 = Article(id=None, headline='NASA uses Python')