Code

Ticket #2248: inline_models_in_Admin.2.diff

File inline_models_in_Admin.2.diff, 5.0 KB (added by JoaoJoao, 8 years ago)

[patch] a *much* better patch for inline_models

Line 
1--- django/db/models/base.py    2006-06-27 15:08:19.000000000 -0300
2+++ django/db/models/base.py    2006-06-27 15:35:35.000000000 -0300
3@@ -150,6 +150,45 @@
4 
5         if hasattr(cls, 'get_absolute_url'):
6             cls.get_absolute_url = curry(get_absolute_url, opts, cls.get_absolute_url)
7+       
8+        # Retrieves the list of fields with related objects
9+        # (Foreign keys)
10+        fk_fields = [x for x in cls._meta.fields if x.rel]
11+        thiscls_fqn = "%s.%s" % (cls.__module__,cls.__name__)
12+        for field in fk_fields:
13+            # Retrieve model that is related to the field
14+            rel_model = field.rel.to
15+            # Check if the related model as a inline_models field
16+            if not hasattr(rel_model,'_meta'):
17+                continue
18+            if rel_model._meta.admin:
19+                for inline_info in rel_model._meta.admin.inline_models:
20+                    model_fqn = inline_info['model']
21+                    if not '.' in model_fqn:
22+                        model_fqn = "%s.%s" % (cls.__module__,model_fqn)
23+                    # There this model is defined in the related model's
24+                    # inline_models entry
25+                    if model_fqn == thiscls_fqn:
26+                        # Set edit_inline and other attributes in the model
27+                        # According to the inline_models entry
28+                        rel_fieldname = inline_info.get('related_field',None)
29+                        # The field name can be set with the 'related_field'
30+                        # argument
31+                        if rel_fieldname:
32+                            rel_field = cls._meta.get_field(rel_fieldname)
33+                        else:
34+                            fields = [x for x in cls._meta.fields if x.rel]
35+                            rel_field = [x for x in fields if  x.rel.to==rel_model][0]
36+                        for key,val in inline_info.iteritems():
37+                            if key=='type':
38+                                rel_field.rel.edit_inline = val
39+                            elif key=='fields':
40+                                for field in cls._meta.fields:
41+                                    if field.name != rel_field.name:
42+                                        field.core = field.name in val
43+                            elif hasattr(rel_field.rel,key):
44+                                setattr(rel_field.rel,key,val)
45+                       
46 
47         dispatcher.send(signal=signals.class_prepared, sender=cls)
48diff -ur --exclude-from=exc django_src/django/db/models/options.py django_src_new/django/db/models/options.py
49--- django/db/models/options.py 2006-06-27 13:31:39.000000000 -0300
50+++ django/db/models/options.py 2006-06-27 10:25:18.000000000 -0300
51@@ -201,7 +201,8 @@
52 class AdminOptions(object):
53     def __init__(self, fields=None, js=None, list_display=None, list_filter=None,
54         date_hierarchy=None, save_as=False, ordering=None, search_fields=None,
55-        save_on_top=False, list_select_related=False, manager=None, list_per_page=100):
56+        save_on_top=False, list_select_related=False, manager=None, list_per_page=100,
57+        inline_models=[]):
58         self.fields = fields
59         self.js = js or []
60         self.list_display = list_display or ['__str__']
61@@ -212,6 +213,7 @@
62         self.save_on_top = save_on_top
63         self.list_select_related = list_select_related
64         self.list_per_page = list_per_page
65+        self.inline_models = inline_models
66         self.manager = manager or Manager()
67 
68     def get_field_sets(self, opts):
69diff -ru --exclude-from=exc django_src_new/docs/model-api.txt django_src/docs/model-api.txt
70--- django/docs/model-api.txt   2006-06-27 10:16:10.000000000 -0300
71+++ django/docs/model-api.txt   2006-06-27 14:00:53.000000000 -0300
72@@ -1176,6 +1176,34 @@
73 under the heading of the fieldset. It's used verbatim, so you can use any HTML
74 and you must escape any special HTML characters (such as ampersands) yourself.
75 
76+``inline_models``
77+-----------------
78+A list of dicts that define which related models should be edited inline with
79+the given model. It's a cleaner alternative to edit_inline, with the
80+following differences:
81+  - You define the model with the 'model' keyword argument. You have to use
82+    the model as a ``string``, not the ``class``.
83+  - You can use the 'related_field' keyword to define the related model's
84+    ForeignKey that will be used, or leave Django to catch the first
85+    ForeignKey field to the parent model.
86+  - Instead of the 'edit_inline' keyword, you use the 'type' keyword.
87+  - Instead of specifying core=True in each field you want to show in
88+    the inline admin, you use the 'fields' keyword argument, which is
89+    a list of fields
90+All other options can be used, e.g. ``min_num_in_admin``.
91+
92+Example::
93+    inline_models = (
94+        {'model':'InlineModel',
95+         'type':models.TABULAR,
96+         'min_num_in_admin':1,
97+         'num_extra_on_change':1,
98+         'fields':('field1','field2','field3')
99+        },
100+    )
101+
102+Check the ``edit_inline`` section for more arguments on this option.
103+
104 ``js``
105 ------
106