diff options
| author | Akis Kesoglou <akiskesoglou@gmail.com> | 2014-02-19 20:01:55 +0200 |
|---|---|---|
| committer | Anssi Kääriäinen <akaariai@gmail.com> | 2014-03-05 22:33:58 +0200 |
| commit | c627da0ccc12861163f28177aa7538b420a9d310 (patch) | |
| tree | d2c3d58f3083bb502f541a9201811e2cdaefd65b /tests/m2m_through | |
| parent | 95c74b9d699c29fe808684774548e2864d64665a (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 'tests/m2m_through')
| -rw-r--r-- | tests/m2m_through/models.py | 36 | ||||
| -rw-r--r-- | tests/m2m_through/tests.py | 29 |
2 files changed, 64 insertions, 1 deletions
diff --git a/tests/m2m_through/models.py b/tests/m2m_through/models.py index 70d6baeca8..aaee0aea3b 100644 --- a/tests/m2m_through/models.py +++ b/tests/m2m_through/models.py @@ -77,3 +77,39 @@ class Friendship(models.Model): first = models.ForeignKey(PersonSelfRefM2M, related_name="rel_from_set") second = models.ForeignKey(PersonSelfRefM2M, related_name="rel_to_set") date_friended = models.DateTimeField() + + +# Custom through link fields +@python_2_unicode_compatible +class Event(models.Model): + title = models.CharField(max_length=50) + invitees = models.ManyToManyField(Person, through='Invitation', through_fields=('event', 'invitee'), related_name='events_invited') + + def __str__(self): + return self.title + + +class Invitation(models.Model): + event = models.ForeignKey(Event, related_name='invitations') + # field order is deliberately inverted. the target field is "invitee". + inviter = models.ForeignKey(Person, related_name='invitations_sent') + invitee = models.ForeignKey(Person, related_name='invitations') + + +@python_2_unicode_compatible +class Employee(models.Model): + name = models.CharField(max_length=5) + subordinates = models.ManyToManyField('self', through="Relationship", through_fields=('source', 'target'), symmetrical=False) + + class Meta: + ordering = ('pk',) + + def __str__(self): + return self.name + + +class Relationship(models.Model): + # field order is deliberately inverted. + another = models.ForeignKey(Employee, related_name="rel_another_set", null=True) + target = models.ForeignKey(Employee, related_name="rel_target_set") + source = models.ForeignKey(Employee, related_name="rel_source_set") diff --git a/tests/m2m_through/tests.py b/tests/m2m_through/tests.py index 0fa3d4aa55..39621bf958 100644 --- a/tests/m2m_through/tests.py +++ b/tests/m2m_through/tests.py @@ -6,7 +6,7 @@ from operator import attrgetter from django.test import TestCase from .models import (Person, Group, Membership, CustomMembership, - PersonSelfRefM2M, Friendship) + PersonSelfRefM2M, Friendship, Event, Invitation, Employee, Relationship) class M2mThroughTests(TestCase): @@ -276,6 +276,33 @@ class M2mThroughTests(TestCase): attrgetter("name") ) + def test_through_fields(self): + """ + Tests that relations with intermediary tables with multiple FKs + to the M2M's ``to`` model are possible. + """ + event = Event.objects.create(title='Rockwhale 2014') + Invitation.objects.create(event=event, inviter=self.bob, invitee=self.jim) + Invitation.objects.create(event=event, inviter=self.bob, invitee=self.jane) + self.assertQuerysetEqual(event.invitees.all(), [ + 'Jane', + 'Jim', + ], attrgetter('name')) + + def test_through_fields_self_referential(self): + john = Employee.objects.create(name='john') + peter = Employee.objects.create(name='peter') + mary = Employee.objects.create(name='mary') + harry = Employee.objects.create(name='harry') + Relationship.objects.create(source=john, target=peter, another=None) + Relationship.objects.create(source=john, target=mary, another=None) + Relationship.objects.create(source=john, target=harry, another=peter) + self.assertQuerysetEqual(john.subordinates.all(), [ + 'peter', + 'mary', + 'harry', + ], attrgetter('name')) + def test_query_tests(self): Membership.objects.create(person=self.jim, group=self.rock) m2 = Membership.objects.create(person=self.jane, group=self.rock) |
