diff -ur --exclude-from=exc django_src/django/db/models/base.py django_src_new/django/db/models/base.py
--- django/db/models/base.py	2006-06-27 13:31:39.000000000 -0300
+++ django/db/models/base.py	2006-06-27 10:23:44.000000000 -0300
@@ -17,6 +17,46 @@
 import types
 import sys
 import os
+try:
+    from threading import local
+except ImportError:
+    from django.utils._threading_local import local
+
+_thread_locals = local()
+
+# This code is needed because we can't connect to the
+# related inline_models' class prepared signals.
+# At the time of class_prepared, the followed model
+# isn't known to Python. So, we store the inline_models
+# info in a variable inside threadlocals
+_thread_locals.inline_models_info = {}
+
+def inline_models_on_class_prepared(**kw_args):
+    sender = kw_args['sender']
+    sender_fqn = "%s.%s" % (sender.__module__,sender.__name__)
+    if sender_fqn in _thread_locals.inline_models_info: 
+        for inline_info in _thread_locals.inline_models_info[sender_fqn]:
+            parent_model = inline_info['parent_model']
+            rel_fieldname = inline_info.get('related_field',None)
+            if rel_fieldname:
+                rel_field = sender._meta.get_field(rel_fieldname) 
+            else:
+                fields = [x for x in sender._meta.fields if x.rel]
+                rel_field = [x for x in fields if  x.rel.to==parent_model][0]
+            for key,val in inline_info.iteritems():
+                if key=='type':
+                    rel_field.rel.edit_inline = val
+                elif key=='fields':
+                    for field in sender._meta.fields:
+                        if field.name != rel_field.name:
+                            field.core = field.name in val
+                elif hasattr(rel_field.rel,key):
+                    setattr(rel_field.rel,key,val)
+        del _thread_locals.inline_models_info[sender_fqn]            
+
+dispatcher.connect(inline_models_on_class_prepared,
+           signal=signals.class_prepared)
+# End of inline_models handling
 
 class ModelBase(type):
     "Metaclass for all models"
@@ -151,6 +191,22 @@
         if hasattr(cls, 'get_absolute_url'):
             cls.get_absolute_url = curry(get_absolute_url, opts, cls.get_absolute_url)
 
+        # Check the inline_models option
+        # and put the corresponding entry in the threadlocals var 
+        # when needed
+        if cls._meta.admin:
+            for inline_info in cls._meta.admin.inline_models:
+                model_name = inline_info['model']
+                if '.' not in model_name:
+                    model_fqn = "%s.%s" % (cls.__module__,model_name)
+                else:
+                    model_fqn = model_name
+                inline_info.update(parent_model=cls)
+                if _thread_locals.inline_models_info.get(model_fqn,None):
+                    _thread_locals.inline_models_info[model_fqn].append(inline_info)
+                else:
+                    _thread_locals.inline_models_info[model_fqn] = [inline_info]
+
         dispatcher.send(signal=signals.class_prepared, sender=cls)
 
     _prepare = classmethod(_prepare)
diff -ur --exclude-from=exc django_src/django/db/models/options.py django_src_new/django/db/models/options.py
--- django/db/models/options.py	2006-06-27 13:31:39.000000000 -0300
+++ django/db/models/options.py	2006-06-27 10:25:18.000000000 -0300
@@ -201,7 +201,8 @@
 class AdminOptions(object):
     def __init__(self, fields=None, js=None, list_display=None, list_filter=None,
         date_hierarchy=None, save_as=False, ordering=None, search_fields=None,
-        save_on_top=False, list_select_related=False, manager=None, list_per_page=100):
+        save_on_top=False, list_select_related=False, manager=None, list_per_page=100,
+        inline_models=[]):
         self.fields = fields
         self.js = js or []
         self.list_display = list_display or ['__str__']
@@ -212,6 +213,7 @@
         self.save_on_top = save_on_top
         self.list_select_related = list_select_related
         self.list_per_page = list_per_page
+        self.inline_models = inline_models
         self.manager = manager or Manager()
 
     def get_field_sets(self, opts):
diff -ru --exclude-from=exc django_src_new/docs/model-api.txt django_src/docs/model-api.txt
--- django/docs/model-api.txt	2006-06-27 10:16:10.000000000 -0300
+++ django/docs/model-api.txt	2006-06-27 14:00:53.000000000 -0300
@@ -1176,6 +1176,34 @@
 under the heading of the fieldset. It's used verbatim, so you can use any HTML
 and you must escape any special HTML characters (such as ampersands) yourself.
 
+``inline_models``
+-----------------
+A list of dicts that define which related models should be edited inline with
+the given model. It's a cleaner alternative to edit_inline, with the
+following differences:
+  - You define the model with the 'model' keyword argument. You have to use
+    the model as a ``string``, not the ``class``.
+  - You can use the 'related_field' keyword to define the related model's
+    ForeignKey that will be used, or leave Django to catch the first
+    ForeignKey field to the parent model.
+  - Instead of the 'edit_inline' keyword, you use the 'type' keyword.
+  - Instead of specifying core=True in each field you want to show in
+    the inline admin, you use the 'fields' keyword argument, which is
+    a list of fields
+All other options can be used, e.g. ``min_num_in_admin``.
+
+Example::
+    inline_models = (
+        {'model':'InlineModel',
+         'type':models.TABULAR,
+         'min_num_in_admin':1,
+         'num_extra_on_change':1,
+         'fields':('field1','field2','field3')
+        },
+    )
+
+Check the ``edit_inline`` section for more arguments on this option.
+
 ``js``
 ------
 
