summaryrefslogtreecommitdiff
path: root/docs/ref
diff options
context:
space:
mode:
authorAkis Kesoglou <akiskesoglou@gmail.com>2014-02-19 20:01:55 +0200
committerAnssi Kääriäinen <akaariai@gmail.com>2014-03-05 22:33:58 +0200
commitc627da0ccc12861163f28177aa7538b420a9d310 (patch)
treed2c3d58f3083bb502f541a9201811e2cdaefd65b /docs/ref
parent95c74b9d699c29fe808684774548e2864d64665a (diff)
Fixed #14549 - Removed restriction of single FKs on intermediary tables
Thanks to Loic Bistuer for review. Minor changes to error messages done by committer.
Diffstat (limited to 'docs/ref')
-rw-r--r--docs/ref/checks.txt9
-rw-r--r--docs/ref/models/fields.txt49
2 files changed, 54 insertions, 4 deletions
diff --git a/docs/ref/checks.txt b/docs/ref/checks.txt
index 908a32d4c8..4f023d2844 100644
--- a/docs/ref/checks.txt
+++ b/docs/ref/checks.txt
@@ -90,10 +90,11 @@ Related Fields
* **fields.E330**: ManyToManyFields cannot be unique.
* **fields.E331**: Field specifies a many-to-many relation through model ``%s``, which has not been installed.
* **fields.E332**: Many-to-many fields with intermediate tables must not be symmetrical.
-* **fields.E333**: The model is used as an intermediate model by ``<model>``, but it has more than two foreign keys to ``<model>``, which is ambiguous.
-* **fields.E334**: The model is used as an intermediate model by ``<model>``, but it has more than one foreign key from ``<model>``, which is ambiguous.
-* **fields.E335**: The model is used as an intermediate model by ``<model>``, but it has more than one foreign key to ``<model>``, which is ambiguous.
-* **fields.E336**: The model is used as an intermediary model by ``<model>``, but it does not have foreign key to ``<model>`` or ``<model>``."
+* **fields.E333**: The model is used as an intermediate model by ``<model>``, but it has more than two foreign keys to ``<model>``, which is ambiguous. You must specify which two foreign keys Django should use via the through_fields keyword argument.
+* **fields.E334**: The model is used as an intermediate model by ``<model>``, but it has more than one foreign key from ``<model>``, which is ambiguous. You must specify which foreign key Django should use via the through_fields keyword argument.
+* **fields.E335**: The model is used as an intermediate model by ``<model>``, but it has more than one foreign key to ``<model>``, which is ambiguous. You must specify which foreign key Django should use via the through_fields keyword argument.
+* **fields.E336**: The model is used as an intermediary model by ``<model>``, but it does not have foreign key to ``<model>`` or ``<model>``.
+* **fields.E337**: The field is given an iterable for through_fields, which does not provide the names for both link fields that Django should use for the relation through <model>.
Signals
~~~~~~~
diff --git a/docs/ref/models/fields.txt b/docs/ref/models/fields.txt
index b3523334c0..ab24dd7e66 100644
--- a/docs/ref/models/fields.txt
+++ b/docs/ref/models/fields.txt
@@ -1337,6 +1337,55 @@ that control how the relationship functions.
:ref:`extra data with a many-to-many relationship
<intermediary-manytomany>`.
+.. attribute:: ManyToManyField.through_fields
+
+ .. versionadded:: 1.7
+
+ Only used when a custom intermediary model is specified. Django will
+ normally determine which fields of the intermediary model to use in order
+ to establish a many-to-many relationship automatically. However,
+ consider the following models::
+
+ from django.db import models
+
+ class Person(models.Model):
+ name = models.CharField(max_length=50)
+
+ class Group(models.Model):
+ name = models.CharField(max_length=128)
+ members = models.ManyToManyField(Person, through='Membership', through_fields=('person', 'group'))
+
+ class Membership(models.Model):
+ person = models.ForeignKey(Person)
+ group = models.ForeignKey(Group)
+ inviter = models.ForeignKey(Person, related_name="membership_invites")
+ invite_reason = models.CharField(max_length=64)
+
+ ``Membership`` has *two* foreign keys to ``Person`` (``person`` and
+ ``inviter``), which makes the relationship ambiguous and Django can't know
+ which one to use. In this case, you must explicitly specify which
+ foreign keys Django should use using ``through_fields``, as in the example
+ above.
+
+ ``through_fields`` accepts a 2-tuple ``('field1', 'field2')``, where
+ ``field1`` is the name of the foreign key to the target model (``person``
+ in this case), and ``field2`` the name of the foreign key to the model the
+ :class:`ManyToManyField` is defined on (``group`` in this case).
+
+ When you have more than one foreign key on an intermediary model to any
+ (or even both) of the models participating in a many-to-many relationship,
+ you *must* specify ``through_fields``. This also applies to
+ :ref:`recursive relationships <recursive-relationships>`
+ when an intermediary model is used and there are more than two
+ foreign keys to the model, or you want to explicitly specify which two
+ Django should use.
+
+ Recursive relationships using an intermediary model are always defined as
+ non-symmetrical -- that is, with :attr:`symmetrical=False <ManyToManyField.symmetrical>`
+ -- therefore, there is the concept of a "source" and a "target". In that
+ case ``'field1'`` will be treated as the "source" of the relationship and
+ ``'field2'`` as the "target".
+
.. attribute:: ManyToManyField.db_table
The name of the table to create for storing the many-to-many data. If this