|
1 from django.core.exceptions import FieldError |
|
2 from django.test import TestCase |
|
3 |
|
4 from models import (SelfRefer, Tag, TagCollection, Entry, SelfReferChild, |
|
5 SelfReferChildSibling, Worksheet) |
|
6 |
|
7 |
|
8 class M2MRegressionTests(TestCase): |
|
9 def assertRaisesErrorWithMessage(self, error, message, callable, *args, **kwargs): |
|
10 self.assertRaises(error, callable, *args, **kwargs) |
|
11 try: |
|
12 callable(*args, **kwargs) |
|
13 except error, e: |
|
14 self.assertEqual(message, str(e)) |
|
15 |
|
16 def test_multiple_m2m(self): |
|
17 # Multiple m2m references to model must be distinguished when |
|
18 # accessing the relations through an instance attribute. |
|
19 |
|
20 s1 = SelfRefer.objects.create(name='s1') |
|
21 s2 = SelfRefer.objects.create(name='s2') |
|
22 s3 = SelfRefer.objects.create(name='s3') |
|
23 s1.references.add(s2) |
|
24 s1.related.add(s3) |
|
25 |
|
26 e1 = Entry.objects.create(name='e1') |
|
27 t1 = Tag.objects.create(name='t1') |
|
28 t2 = Tag.objects.create(name='t2') |
|
29 |
|
30 e1.topics.add(t1) |
|
31 e1.related.add(t2) |
|
32 |
|
33 self.assertQuerysetEqual(s1.references.all(), ["<SelfRefer: s2>"]) |
|
34 self.assertQuerysetEqual(s1.related.all(), ["<SelfRefer: s3>"]) |
|
35 |
|
36 self.assertQuerysetEqual(e1.topics.all(), ["<Tag: t1>"]) |
|
37 self.assertQuerysetEqual(e1.related.all(), ["<Tag: t2>"]) |
|
38 |
|
39 def test_internal_related_name_not_in_error_msg(self): |
|
40 # The secret internal related names for self-referential many-to-many |
|
41 # fields shouldn't appear in the list when an error is made. |
|
42 |
|
43 self.assertRaisesErrorWithMessage(FieldError, |
|
44 "Cannot resolve keyword 'porcupine' into field. Choices are: id, name, references, related, selfreferchild, selfreferchildsibling", |
|
45 lambda: SelfRefer.objects.filter(porcupine='fred') |
|
46 ) |
|
47 |
|
48 def test_m2m_inheritance_symmetry(self): |
|
49 # Test to ensure that the relationship between two inherited models |
|
50 # with a self-referential m2m field maintains symmetry |
|
51 |
|
52 sr_child = SelfReferChild(name="Hanna") |
|
53 sr_child.save() |
|
54 |
|
55 sr_sibling = SelfReferChildSibling(name="Beth") |
|
56 sr_sibling.save() |
|
57 sr_child.related.add(sr_sibling) |
|
58 |
|
59 self.assertQuerysetEqual(sr_child.related.all(), ["<SelfRefer: Beth>"]) |
|
60 self.assertQuerysetEqual(sr_sibling.related.all(), ["<SelfRefer: Hanna>"]) |
|
61 |
|
62 def test_m2m_pk_field_type(self): |
|
63 # Regression for #11311 - The primary key for models in a m2m relation |
|
64 # doesn't have to be an AutoField |
|
65 |
|
66 w = Worksheet(id='abc') |
|
67 w.save() |
|
68 w.delete() |
|
69 |
|
70 def test_add_m2m_with_base_class(self): |
|
71 # Regression for #11956 -- You can add an object to a m2m with the |
|
72 # base class without causing integrity errors |
|
73 |
|
74 t1 = Tag.objects.create(name='t1') |
|
75 t2 = Tag.objects.create(name='t2') |
|
76 |
|
77 c1 = TagCollection.objects.create(name='c1') |
|
78 c1.tags = [t1,t2] |
|
79 c1 = TagCollection.objects.get(name='c1') |
|
80 |
|
81 self.assertQuerysetEqual(c1.tags.all(), ["<Tag: t1>", "<Tag: t2>"]) |
|
82 self.assertQuerysetEqual(t1.tag_collections.all(), ["<TagCollection: c1>"]) |