Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Newer
Older
100644 990 lines (746 sloc) 44.406 kb
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
1 ================================
2 Chapter 6: The Django Admin Site
3 ================================
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
4
5 For a certain class of Web sites, an *admin interface* is an essential part of
6 the infrastructure. This is a Web-based interface, limited to trusted site
7 administrators, that enables the adding, editing and deletion of site content.
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
8 Some common examples: the interface you use to post to your blog, the backend
9 site managers use to moderate user-generated comments, the tool your clients
10 use to update the press releases on the Web site you built for them.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
11
12 There's a problem with admin interfaces, though: it's boring to build them.
13 Web development is fun when you're developing public-facing functionality, but
14 building admin interfaces is always the same. You have to authenticate users,
15 display and handle forms, validate input, and so on. It's boring, and it's
16 repetitive.
17
18 So what's Django's approach to these boring, repetitive tasks? It does it all
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
19 for you -- in just a couple of lines of code, no less. With Django, building an
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
20 admin interface is a solved problem.
21
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
22 This chapter is about Django's automatic admin interface. The feature works by
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
23 reading metadata in your model to provide a powerful and production-ready
24 interface that site administrators can start using immediately. Here, we discuss
25 how to activate, use, and customize this feature.
26
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
27 Note that we recommend reading this chapter even if you don't intend to use the
28 Django admin site, because we introduce a few concepts that apply to all of
29 Django, regardless of admin-site usage.
30
31 The django.contrib packages
32 ===========================
33
34 Django's automatic admin is part of a larger suite of Django functionality
35 called ``django.contrib`` -- the part of the Django codebase that contains
36 various useful add-ons to the core framework. You can think of
37 ``django.contrib`` as Django's equivalent of the Python standard library --
38 optional, de facto implementations of common patterns. They're bundled with
39 Django so that you don't have to reinvent the wheel in your own applications.
40
41 The admin site is the first part of ``django.contrib`` that we're covering in
42 this book; technically, it's called ``django.contrib.admin``. Other available
43 features in ``django.contrib`` include a user authentication system
44 (``django.contrib.auth``), support for anonymous sessions
45 (``django.contrib.sessions``) and even a system for user comments
46 (``django.contrib.comments``). You'll get to know the various ``django.contrib``
47 features as you become a Django expert, and we'll spend some more time
48 discussing them in Chapter 16. For now, just know that Django ships with many
49 nice add-ons, and ``django.contrib`` is generally where they live.
50
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
51 Activating the Admin Interface
52 ==============================
53
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
54 The Django admin site is entirely optional, because only certain types of sites
55 need this functionality. That means you'll need to take a few steps to activate
56 it in your project.
57
58 First, make a few changes to your settings file:
59
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
60 1. Add ``'django.contrib.admin'`` to the ``INSTALLED_APPS`` setting. (The
61 order of ``INSTALLED_APPS`` doesn't matter, but we like to keep things
62 alphabetical so it's easy for a human to read.)
63
64 2. Make sure ``INSTALLED_APPS`` contains ``'django.contrib.auth'``,
65 ``'django.contrib.contenttypes'`` and ``'django.contrib.sessions'``. The
66 Django admin site requires these three packages. (If you're following
67 along with our ongoing ``mysite`` project, note that we commented out
68 these three ``INSTALLED_APPS`` entries in Chapter 5. Uncomment them now.)
69
70 3. Make sure ``MIDDLEWARE_CLASSES`` contains
71 ``'django.middleware.common.CommonMiddleware'``,
72 ``'django.contrib.sessions.middleware.SessionMiddleware'`` and
73 ``'django.contrib.auth.middleware.AuthenticationMiddleware'``. (Again,
74 if you're following along, note that we commented them out in Chapter 5,
75 so uncomment them.)
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
76
77 Second, run ``python manage.py syncdb``. This step will install the extra
78 database tables that the admin interface uses. The first time you run
79 ``syncdb`` with ``'django.contrib.auth'`` in ``INSTALLED_APPS``, you'll be
80 asked about creating a superuser. If you don't do this, you'll need to run
81 ``python manage.py createsuperuser`` separately to create an admin user
82 account; otherwise, you won't be able to log in to the admin site. (Potential
83 gotcha: the ``python manage.py createsuperuser`` command is only available if
84 ``'django.contrib.auth'`` is in your ``INSTALLED_APPS``.)
85
86 Third, add the admin site to your URLconf (in ``urls.py``, remember). By
87 default, the ``urls.py`` generated by ``django-admin.py startproject`` contains
88 commented-out code for the Django admin, and all you have to do is uncomment
89 it. For the record, here are the bits you need to make sure are in there::
90
91 # Include these import statements...
92 from django.contrib import admin
93 admin.autodiscover()
94
95 # And include this URLpattern...
96 urlpatterns = patterns('',
97 # ...
98 (r'^admin/', include(admin.site.urls)),
99 # ...
100 )
101
102 With that bit of configuration out of the way, now you can see the Django
103 admin site in action. Just run the development server
104 (``python manage.py runserver``, as in previous chapters) and visit
105 ``http://127.0.0.1:8000/admin/`` in your Web browser.
106
107 Using the Admin Site
108 ====================
109
110 The admin site is designed to be used by nontechnical users, and as such it
111 should be pretty self-explanatory. Nevertheless, we'll give you a quick
112 walkthrough of the basic features.
113
114 The first thing you'll see is a login screen, as shown in Figure 6-1.
115
116 .. figure:: graphics/chapter06/login.png
117 :alt: Screenshot of Django's login page.
118
119 Figure 6-1. Django's login screen
120
121 Log in with the username and password you set up when you added your superuser.
122 If you're unable to log in, make sure you've actually created a superuser --
123 try running ``python manage.py createsuperuser``.
124
125 Once you're logged in, the first thing you'll see will be the admin home page.
126 This page lists all the available types of data that can be edited on the admin
127 site. At this point, because we haven't activated any of our own models yet,
128 the list is sparse: it includes only Groups and Users, which are the two
129 default admin-editable models.
130
131 .. DWP The screenshot contains books etc too.
132
133 .. figure:: graphics/chapter06/admin_index.png
134 :alt: Screenshot of the Django admin home page.
135
136 Figure 6-2. The Django admin home page
137
138 Each type of data in the Django admin site has a *change list* and an
139 *edit form*. Change lists show you all the available objects in the database,
140 and edit forms let you add, change or delete particular records in your
141 database.
142
143 .. admonition:: Other languages
144
145 If your primary language is not English and your Web browser is configured
146 to prefer a language other than English, you can make a quick change to
147 see whether the Django admin site has been translated into your language.
148 Just add ``'django.middleware.locale.LocaleMiddleware'`` to your
149 ``MIDDLEWARE_CLASSES`` setting, making sure it appears *after*
150 ``'django.contrib.sessions.middleware.SessionMiddleware'``.
151
152 When you've done that, reload the admin index page. If a translation for
153 your language is available, then the various parts of the interface -- from
154 the "Change password" and "Log out" links at the top of the page, to the
155 "Groups" and "Users" links in the middle -- will appear in your language
156 instead of English. Django ships with translations for dozens of languages.
157
158 For much more on Django's internationalization features, see Chapter 19.
159
160 Click the "Change" link in the "Users" row to load the change list page for
161 users.
162
163 .. figure:: graphics/chapter06/user_changelist.png
164 :alt: Screenshot of the user change list page.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
165
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
166 Figure 6-3. The user change list page
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
167
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
168 .. DWP This screenshot is actually the list for books.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
169
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
170 This page displays all users in the database; you can think of it as a
171 prettied-up Web version of a ``SELECT * FROM auth_user;`` SQL query. If you're
172 following along with our ongoing example, you'll only see one user here,
173 assuming you've added only one, but once you have more users, you'll probably
174 find the filtering, sorting and searching options useful. Filtering options are
175 at right, sorting is available by clicking a column header, and the search box
176 at the top lets you search by username.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
177
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
178 Click the username of the user you created, and you'll see the edit form for
179 that user.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
180
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
181 .. figure:: graphics/chapter06/user_editform.png
182 :alt: Screenshot of the user edit form
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
183
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
184 Figure 6-4. The user edit form
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
185
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
186 .. DWP The edit form screenshot is for a book.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
187
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
188 This page lets you change the attributes of the user, like the
189 first/last names and various permissions. (Note that to change a user's
190 password, you should click "change password form" under the password field
191 rather than editing the hashed code.) Another thing to note here is that fields
192 of different types get different widgets -- for example, date/time fields have
193 calendar controls, boolean fields have checkboxes, character fields have simple
194 text input fields.
195
196 You can delete a record by clicking the delete button at the bottom left of its
197 edit form. That'll take you to a confirmation page, which, in some cases, will
198 display any dependent objects that will be deleted, too. (For example, if you
199 delete a publisher, any book with that publisher will be deleted, too!)
200
201 You can add a record by clicking "Add" in the appropriate column of the admin
202 home page. This will give you an empty version of the edit page, ready for you
203 to fill out.
204
205 You'll also notice that the admin interface also handles input validation for
206 you. Try leaving a required field blank or putting an invalid date into a date
207 field, and you'll see those errors when you try to save, as shown in Figure 6-5.
208
209 .. figure:: graphics/chapter06/user_editform_errors.png
210 :alt: Screenshot of an edit form displaying errors.
211
212 Figure 6-5. An edit form displaying errors
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
213
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
214 .. DWP The screenshots are still following a book example.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
215
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
216 When you edit an existing object, you'll notice a History link in the
217 upper-right corner of the window. Every change made through the admin interface
218 is logged, and you can examine this log by clicking the History link (see
219 Figure 6-6).
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
220
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
221 .. figure:: graphics/chapter06/user_history.png
222 :alt: Screenshot of an object history page.
223
224 Figure 6-6. An object history page
225
226 .. DWP Still using a book in the pictures.
227
228 Adding Your Models to the Admin Site
229 ====================================
230
231 There's one crucial part we haven't done yet. Let's add our own models to the
232 admin site, so we can add, change and delete objects in our custom database
233 tables using this nice interface. We'll continue the ``books`` example from
234 Chapter 5, where we defined three models: ``Publisher``, ``Author`` and
235 ``Book``.
236
237 Within the ``books`` directory (``mysite/books``), create a file called
238 ``admin.py``, and type in the following lines of code::
239
240 from django.contrib import admin
241 from mysite.books.models import Publisher, Author, Book
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
242
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
243 admin.site.register(Publisher)
244 admin.site.register(Author)
245 admin.site.register(Book)
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
246
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
247 This code tells the Django admin site to offer an interface for each of these
248 models.
249
250 Once you've done this, go to your admin home page in your Web browser
251 (``http://127.0.0.1:8000/admin/``), and you should see a "Books" section with
252 links for Authors, Books and Publishers. (You might have to stop and start the
253 ``runserver`` for the changes to take effect.)
254
255 .. SL Tested ok
256
257 You now have a fully functional admin interface for each of those three models.
258 That was easy!
259
260 Take some time to add and change records, to populate your database with some
261 data. If you followed Chapter 5's examples of creating ``Publisher`` objects
262 (and you didn't delete them), you'll already see those records on the publisher
263 change list page.
264
265 One feature worth mentioning here is the admin site's handling of foreign keys
266 and many-to-many relationships, both of which appear in the ``Book`` model. As
267 a reminder, here's what the ``Book`` model looks like::
268
269 class Book(models.Model):
270 title = models.CharField(max_length=100)
271 authors = models.ManyToManyField(Author)
272 publisher = models.ForeignKey(Publisher)
273 publication_date = models.DateField()
274
275 def __unicode__(self):
276 return self.title
277
278 On the Django admin site's "Add book" page
279 (``http://127.0.0.1:8000/admin/books/book/add/``), the publisher (a
280 ``ForeignKey``) is represented by a select box, and the authors field
281 (a ``ManyToManyField``) is represented by a multiple-select box. Both fields
282 sit next to a green plus sign icon that lets you add related records of that
283 type. For example, if you click the green plus sign next to the "Publisher"
284 field, you'll get a pop-up window that lets you add a publisher. After you
285 successfully create the publisher in the pop-up, the "Add book" form will be
286 updated with the newly created publisher. Slick.
287
288 How the Admin Site Works
289 ========================
290
291 Behind the scenes, how does the admin site work? It's pretty straightforward.
292
293 When Django loads your URLconf from ``urls.py`` at server startup, it executes
294 the ``admin.autodiscover()`` statement that we added as part of activating the
295 admin. This function iterates over your ``INSTALLED_APPS`` setting and looks
296 for a file called ``admin.py`` in each installed app. If an ``admin.py``
297 exists in a given app, it executes the code in that file.
298
299 In the ``admin.py`` in our ``books`` app, each call to
300 ``admin.site.register()`` simply registers the given model with the admin. The
301 admin site will only display an edit/change interface for models that have been
302 explicitly registered.
303
304 The app ``django.contrib.auth`` includes its own ``admin.py``, which is why
305 Users and Groups showed up automatically in the admin. Other ``django.contrib``
306 apps, such as ``django.contrib.redirects``, also add themselves to the admin,
307 as do many third-party Django applications you might download from the Web.
308
309 Beyond that, the Django admin site is just a Django application, with its own
310 models, templates, views and URLpatterns. You add it to your application by
311 hooking it into your URLconf, just as you hook in your own views. You can
312 inspect its templates, views and URLpatterns by poking around in
313 ``django/contrib/admin`` in your copy of the Django codebase -- but don't be
314 tempted to change anything directly in there, as there are plenty of hooks for
315 you to customize the way the admin site works. (If you do decide to poke around
316 the Django admin application, keep in mind it does some rather complicated
317 things in reading metadata about models, so it would probably take a good
318 amount of time to read and understand the code.)
319
320 Making Fields Optional
321 ======================
322
323 After you play around with the admin site for a while, you'll probably notice a
324 limitation -- the edit forms require every field to be filled out, whereas in
325 many cases you'd want certain fields to be optional. Let's say, for example,
326 that we want our ``Author`` model's ``email`` field to be optional -- that is,
327 a blank string should be allowed. In the real world, you might not have an
328 e-mail address on file for every author.
329
330 To specify that the ``email`` field is optional, edit the ``Book`` model
331 (which, as you'll recall from Chapter 5, lives in ``mysite/books/models.py``).
332 Simply add ``blank=True`` to the ``email`` field, like so:
333
334 .. parsed-literal::
335
336 class Author(models.Model):
337 first_name = models.CharField(max_length=30)
338 last_name = models.CharField(max_length=40)
339 email = models.EmailField(**blank=True**)
340
341 .. SL Tested ok
342
343 This tells Django that a blank value is indeed allowed for authors' e-mail
344 addresses. By default, all fields have ``blank=False``, which means blank
345 values are not allowed.
346
347 There's something interesting happening here. Until now, with the exception of
348 the ``__unicode__()`` method, our models have served as definitions of our
349 database tables -- Pythonic expressions of SQL ``CREATE TABLE`` statements,
350 essentially. In adding ``blank=True``, we have begun expanding our model beyond
351 a simple definition of what the database table looks like. Now, our model class
352 is starting to become a richer collection of knowledge about what ``Author``
353 objects are and what they can do. Not only is the ``email`` field represented
354 by a ``VARCHAR`` column in the database; it's also an optional field in
355 contexts such as the Django admin site.
356
357 Once you've added that ``blank=True``, reload the "Add author" edit form
358 (``http://127.0.0.1:8000/admin/books/author/add/``), and you'll notice the
359 field's label -- "Email" -- is no longer bolded. This signifies it's not a
360 required field. You can now add authors without needing to provide
361 e-mail addresses; you won't get the loud red "This field is required" message
362 anymore, if the field is submitted empty.
363
364 Making Date and Numeric Fields Optional
365 ---------------------------------------
366
367 A common gotcha related to ``blank=True`` has to do with date and numeric
368 fields, but it requires a fair amount of background explanation.
369
370 SQL has its own way of specifying blank values -- a special value called
371 ``NULL``. ``NULL`` could mean "unknown," or "invalid," or some other
372 application-specific meaning.
373
374 In SQL, a value of ``NULL`` is different than an empty string, just as the
375 special Python object ``None`` is different than an empty Python string
376 (``""``). This means it's possible for a particular character field (e.g., a
377 ``VARCHAR`` column) to contain both ``NULL`` values and empty string values.
378
379 This can cause unwanted ambiguity and confusion: "Why does this record have a
380 ``NULL`` but this other one has an empty string? Is there a difference, or was
381 the data just entered inconsistently?" And: "How do I get all the records that
382 have a blank value -- should I look for both ``NULL`` records and empty
383 strings, or do I only select the ones with empty strings?"
384
385 To help avoid such ambiguity, Django's automatically generated ``CREATE TABLE``
386 statements (which were covered in Chapter 5) add an explicit ``NOT NULL`` to
387 each column definition. For example, here's the generated statement for our
388 ``Author`` model, from Chapter 5::
389
390 CREATE TABLE "books_author" (
391 "id" serial NOT NULL PRIMARY KEY,
392 "first_name" varchar(30) NOT NULL,
393 "last_name" varchar(40) NOT NULL,
394 "email" varchar(75) NOT NULL
395 )
396 ;
397
398 In most cases, this default behavior is optimal for your application and will
399 save you from data-inconsistency headaches. And it works nicely with the rest
400 of Django, such as the Django admin site, which inserts an empty string (*not*
401 a ``NULL`` value) when you leave a character field blank.
402
403 But there's an exception with database column types that do not accept empty
404 strings as valid values -- such as dates, times and numbers. If you try to
405 insert an empty string into a date or integer column, you'll likely get a
406 database error, depending on which database you're using. (PostgreSQL, which is
407 strict, will raise an exception here; MySQL might accept it or might not,
408 depending on the version you're using, the time of day and the phase of the
409 moon.) In this case, ``NULL`` is the only way to specify an empty
410 value. In Django models, you can specify that ``NULL`` is allowed by adding
411 ``null=True`` to a field.
412
413 So that's a long way of saying this: if you want to allow blank values in a
414 date field (e.g., ``DateField``, ``TimeField``, ``DateTimeField``) or numeric
415 field (e.g., ``IntegerField``, ``DecimalField``, ``FloatField``), you'll need
416 to use both ``null=True`` *and* ``blank=True``.
417
418 For sake of example, let's change our ``Book`` model to allow a blank
419 ``publication_date``. Here's the revised code:
420
421 .. parsed-literal::
422
423 class Book(models.Model):
424 title = models.CharField(max_length=100)
425 authors = models.ManyToManyField(Author)
426 publisher = models.ForeignKey(Publisher)
427 publication_date = models.DateField(**blank=True, null=True**)
428
429 .. SL Tested ok
430
431 Adding ``null=True`` is more complicated than adding ``blank=True``, because
432 ``null=True`` changes the semantics of the database -- that is, it changes the
433 ``CREATE TABLE`` statement to remove the ``NOT NULL`` from the
434 ``publication_date`` field. To complete this change, we'll need to update the
435 database.
436
437 For a number of reasons, Django does not attempt to automate changes to
438 database schemas, so it's your own responsibility to execute the appropriate
439 ``ALTER TABLE`` statement whenever you make such a change to a model. Recall
440 that you can use ``manage.py dbshell`` to enter your database server's shell.
441 Here's how to remove the ``NOT NULL`` in this particular case::
442
443 ALTER TABLE books_book ALTER COLUMN publication_date DROP NOT NULL;
444
445 (Note that this SQL syntax is specific to PostgreSQL.)
446
447 We'll cover schema changes in more depth in Chapter 10.
448
449 Bringing this back to the admin site, now the "Add book" edit form should allow
450 for empty publication date values.
451
452 Customizing Field Labels
453 ========================
454
455 On the admin site's edit forms, each field's label is generated from its model
456 field name. The algorithm is simple: Django just replaces underscores with
457 spaces and capitalizes the first character, so, for example, the ``Book``
458 model's ``publication_date`` field has the label "Publication date."
459
460 However, field names don't always lend themselves to nice admin field labels,
461 so in some cases you might want to customize a label. You can do this by
462 specifying ``verbose_name`` in the appropriate model field.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
463
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
464 For example, here's how we can change the label of the ``Author.email`` field
465 to "e-mail," with a hyphen:
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
466
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
467 .. parsed-literal::
468
469 class Author(models.Model):
470 first_name = models.CharField(max_length=30)
471 last_name = models.CharField(max_length=40)
472 email = models.EmailField(blank=True, **verbose_name='e-mail'**)
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
473
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
474 Make that change and reload the server, and you should see the field's new
475 label on the author edit form.
476
477 Note that you shouldn't capitalize the first letter of a ``verbose_name``
478 unless it should *always* be capitalized (e.g., ``"USA state"``). Django will
479 automatically capitalize it when it needs to, and it will use the exact
480 ``verbose_name`` value in other places that don't require capitalization.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
481
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
482 Finally, note that you can pass the ``verbose_name`` as a positional argument,
483 for a slightly more compact syntax. This example is equivalent to the previous
484 one:
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
485
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
486 .. parsed-literal::
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
487
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
488 class Author(models.Model):
489 first_name = models.CharField(max_length=30)
490 last_name = models.CharField(max_length=40)
491 email = models.EmailField(**'e-mail',** blank=True)
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
492
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
493 .. SL Tested ok
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
494
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
495 This won't work with ``ManyToManyField`` or ``ForeignKey`` fields, though,
496 because they require the first argument to be a model class. In those cases,
497 specifying ``verbose_name`` explicitly is the way to go.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
498
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
499 Custom ModelAdmin classes
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
500 =========================
501
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
502 The changes we've made so far -- ``blank=True``, ``null=True`` and
503 ``verbose_name`` -- are really model-level changes, not admin-level changes.
504 That is, these changes are fundamentally a part of the model and just so happen
505 to be used by the admin site; there's nothing admin-specific about them.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
506
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
507 Beyond these, the Django admin site offers a wealth of options that let you
508 customize how the admin site works for a particular model. Such options live in
509 *ModelAdmin classes*, which are classes that contain configuration for a
510 specific model in a specific admin site instance.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
511
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
512 Customizing change lists
513 ------------------------
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
514
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
515 Let's dive into admin customization by specifying the fields that are
516 displayed on the change list for our ``Author`` model. By default, the change
517 list displays the result of ``__unicode__()`` for each object. In Chapter 5, we
518 defined the ``__unicode__()`` method for ``Author`` objects to display the
519 first name and last name together:
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
520
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
521 .. parsed-literal::
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
522
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
523 class Author(models.Model):
524 first_name = models.CharField(max_length=30)
525 last_name = models.CharField(max_length=40)
526 email = models.EmailField(blank=True, verbose_name='e-mail')
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
527
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
528 **def __unicode__(self):**
529 **return u'%s %s' % (self.first_name, self.last_name)**
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
530
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
531 As a result, the change list for ``Author`` objects displays each other's
532 first name and last name together, as you can see in Figure 6-7.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
533
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
534 .. DWP The image is of the change list for a book, not an author.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
535
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
536 .. figure:: graphics/chapter06/author_changelist1.png
537 :alt: Screenshot of the author change list page.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
538
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
539 Figure 6-7. The author change list page
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
540
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
541 We can improve on this default behavior by adding a few other fields to the
542 change list display. It'd be handy, for example, to see each author's e-mail
543 address in this list, and it'd be nice to be able to sort by first and last
544 name.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
545
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
546 To make this happen, we'll define a ``ModelAdmin`` class for the ``Author``
547 model. This class is the key to customizing the admin, and one of the most
548 basic things it lets you do is specify the list of fields to display on change
549 list pages. Edit ``admin.py`` to make these changes:
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
550
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
551 .. parsed-literal::
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
552
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
553 from django.contrib import admin
554 from mysite.books.models import Publisher, Author, Book
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
555
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
556 **class AuthorAdmin(admin.ModelAdmin):**
557 **list_display = ('first_name', 'last_name', 'email')**
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
558
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
559 admin.site.register(Publisher)
560 **admin.site.register(Author, AuthorAdmin)**
561 admin.site.register(Book)
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
562
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
563 .. SL Tested ok
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
564
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
565 Here's what we've done:
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
566
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
567 * We created the class ``AuthorAdmin``. This class, which subclasses
568 ``django.contrib.admin.ModelAdmin``, holds custom configuration
569 for a specific admin model. We've only specified one customization --
570 ``list_display``, which is set to a tuple of field names to display on
571 the change list page. These field names must exist in the model, of
572 course.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
573
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
574 * We altered the ``admin.site.register()`` call to add ``AuthorAdmin`` after
575 ``Author``. You can read this as: "Register the ``Author`` model with the
576 ``AuthorAdmin`` options."
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
577
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
578 The ``admin.site.register()`` function takes a ``ModelAdmin`` subclass as
579 an optional second argument. If you don't specify a second argument (as
580 is the case for ``Publisher`` and ``Book``), Django will use the default
581 admin options for that model.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
582
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
583 With that tweak made, reload the author change list page, and you'll see it's
584 now displaying three columns -- the first name, last name and e-mail address.
585 In addition, each of those columns is sortable by clicking on the column
586 header. (See Figure 6-8.)
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
587
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
588 .. figure:: graphics/chapter06/author_changelist2.png
589 :alt: Screenshot of the author change list page after list_display.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
590
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
591 Figure 6-8. The author change list page after list_display
592
593 .. DWP This figure has the same filename as the last one.
594
595 Next, let's add a simple search bar. Add ``search_fields`` to the
596 ``AuthorAdmin``, like so:
597
598 .. parsed-literal::
599
600 class AuthorAdmin(admin.ModelAdmin):
601 list_display = ('first_name', 'last_name', 'email')
602 **search_fields = ('first_name', 'last_name')**
603
604 .. SL Tested ok
605
606 Reload the page in your browser, and you should see a search bar at the top.
607 (See Figure 6-9.) We've just told the admin change list page to include a
608 search bar that searches against the ``first_name`` and ``last_name`` fields.
609 As a user might expect, this is case-insensitive and searches both fields, so
610 searching for the string ``"bar"`` would find both an author with the first
611 name Barney and an author with the last name Hobarson.
612
613 .. DWP Again, same screenshot.
614
615 .. figure:: graphics/chapter06/author_changelist3.png
616 :alt: Screenshot of the author change list page after search_fields.
617
618 Figure 6-9. The author change list page after search_fields
619
620 Next, let's add some date filters to our ``Book`` model's change list page:
621
622 .. parsed-literal::
623
624 from django.contrib import admin
625 from mysite.books.models import Publisher, Author, Book
626
627 class AuthorAdmin(admin.ModelAdmin):
628 list_display = ('first_name', 'last_name', 'email')
629 search_fields = ('first_name', 'last_name')
630
631 **class BookAdmin(admin.ModelAdmin):**
632 **list_display = ('title', 'publisher', 'publication_date')**
633 **list_filter = ('publication_date',)**
634
635 admin.site.register(Publisher)
636 admin.site.register(Author, AuthorAdmin)
637 **admin.site.register(Book, BookAdmin)**
638
639 .. SL Tested ok
640
641 Here, because we're dealing with a different set of options, we created a
642 separate ``ModelAdmin`` class -- ``BookAdmin``. First, we defined a
643 ``list_display`` just to make the change list look a bit nicer. Then, we
644 used ``list_filter``, which is set to a tuple of fields to use to create
645 filters along the right side of the change list page. For date fields, Django
646 provides shortcuts to filter the list to "Today," "Past 7 days," "This month"
647 and "This year" -- shortcuts that Django's developers have found hit the
648 common cases for filtering by date. Figure 6-10 shows what that looks like.
649
650 .. DWP Screenshot needs changing.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
651
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
652 .. figure:: graphics/chapter06/book_changelist1.png
653 :alt: Screenshot of the book change list page after list_filter.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
654
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
655 Figure 6-10. The book change list page after list_filter
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
656
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
657 ``list_filter`` also works on fields of other types, not just ``DateField``.
658 (Try it with ``BooleanField`` and ``ForeignKey`` fields, for example.) The
659 filters show up as long as there are at least 2 values to choose from.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
660
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
661 Another way to offer date filters is to use the ``date_hierarchy`` admin
662 option, like this:
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
663
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
664 .. parsed-literal::
665
666 class BookAdmin(admin.ModelAdmin):
667 list_display = ('title', 'publisher', 'publication_date')
668 list_filter = ('publication_date',)
669 **date_hierarchy = 'publication_date'**
670
671 .. SL Tested ok
672
673 With this in place, the change list page gets a date drill-down navigation bar
674 at the top of the list, as shown in Figure 6-11. It starts with a list of
675 available years, then drills down into months and individual days.
676
677 .. DWP Screenshot again.
678
679 .. figure:: graphics/chapter06/book_changelist2.png
680 :alt: Screenshot of the book change list page after date_hierarchy.
681
682 Figure 6-11. The book change list page after date_hierarchy
683
684 Note that ``date_hierarchy`` takes a *string*, not a tuple, because only one
685 date field can be used to make the hierarchy.
686
687 Finally, let's change the default ordering so that books on the change list
688 page are always ordered descending by their publication date. By default,
689 the change list orders objects according to their model's ``ordering`` within
690 ``class Meta`` (which we covered in Chapter 5) -- but you haven't specified
691 this ``ordering`` value, then the ordering is undefined.
692
693 .. parsed-literal::
694
695 class BookAdmin(admin.ModelAdmin):
696 list_display = ('title', 'publisher', 'publication_date')
697 list_filter = ('publication_date',)
698 date_hierarchy = 'publication_date'
699 **ordering = ('-publication_date',)**
700
701 .. SL Tested ok
702
703 This admin ``ordering`` option works exactly as the ``ordering`` in models'
704 ``class Meta``, except that it only uses the first field name in the list. Just
705 pass a list or tuple of field names, and add a minus sign to a field to use
706 descending sort order.
707
708 Reload the book change list to see this in action. Note that the
709 "Publication date" header now includes a small arrow that indicates which way
710 the records are sorted. (See Figure 6-12.)
711
712 .. DWP Different screenshot needed.
713
714 .. figure:: graphics/chapter06/book_changelist3.png
715 :alt: Screenshot of the book change list page after ordering.
716
717 Figure 6-12. The book change list page after ordering
718
719 We've covered the main change list options here. Using these options, you can
720 make a very powerful, production-ready data-editing interface with only a few
721 lines of code.
722
723 Customizing edit forms
724 ----------------------
725
726 Just as the change list can be customized, edit forms can be customized in many
727 ways.
728
729 First, let's customize the way fields are ordered. By default, the order of
730 fields in an edit form corresponds to the order they're defined in the model.
731 We can change that using the ``fields`` option in our ``ModelAdmin`` subclass:
732
733 .. parsed-literal::
734
735 class BookAdmin(admin.ModelAdmin):
736 list_display = ('title', 'publisher', 'publication_date')
737 list_filter = ('publication_date',)
738 date_hierarchy = 'publication_date'
739 ordering = ('-publication_date',)
740 **fields = ('title', 'authors', 'publisher', 'publication_date')**
741
742 .. SL Tested ok
743
744 After this change, the edit form for books will use the given ordering for
745 fields. It's slightly more natural to have the authors after the book title.
746 Of course, the field order should depend on your data-entry workflow. Every
747 form is different.
748
749 Another useful thing the ``fields`` option lets you do is to *exclude* certain
750 fields from being edited entirely. Just leave out the field(s) you want to
751 exclude. You might use this if your admin users are only trusted to edit a
752 certain segment of your data, or if part of your fields are changed by some
753 outside, automated process. For example, in our book database, we could
754 hide the ``publication_date`` field from being editable:
755
756 .. parsed-literal::
757
758 class BookAdmin(admin.ModelAdmin):
759 list_display = ('title', 'publisher', 'publication_date')
760 list_filter = ('publication_date',)
761 date_hierarchy = 'publication_date'
762 ordering = ('-publication_date',)
763 **fields = ('title', 'authors', 'publisher')**
764
765 .. SL Tested ok
766
767 As a result, the edit form for books doesn't offer a way to specify the
768 publication date. This could be useful, say, if you're an editor who prefers
769 that his authors not push back publication dates. (This is purely a
770 hypothetical example, of course.)
771
772 When a user uses this incomplete form to add a new book, Django will simply set
773 the ``publication_date`` to ``None`` -- so make sure that field has
774 ``null=True``.
775
776 Another commonly used edit-form customization has to do with many-to-many
777 fields. As we've seen on the edit form for books, the admin site represents each
778 ``ManyToManyField`` as a multiple-select boxes, which is the most logical
779 HTML input widget to use -- but multiple-select boxes can be difficult to use.
780 If you want to select multiple items, you have to hold down the control key,
781 or command on a Mac, to do so. The admin site helpfully inserts a bit of text
782 that explains this, but, still, it gets unwieldy when your field contains
783 hundreds of options.
784
785 The admin site's solution is ``filter_horizontal``. Let's add that to
786 ``BookAdmin`` and see what it does.
787
788 .. parsed-literal::
789
790 class BookAdmin(admin.ModelAdmin):
791 list_display = ('title', 'publisher', 'publication_date')
792 list_filter = ('publication_date',)
793 date_hierarchy = 'publication_date'
794 ordering = ('-publication_date',)
795 **filter_horizontal = ('authors',)**
796
797 .. SL Tested ok
798
799 (If you're following along, note that we've also removed the ``fields`` option
800 to restore all the fields in the edit form.)
801
802 Reload the edit form for books, and you'll see that the "Authors" section now
803 uses a fancy JavaScript filter interface that lets you search through the
804 options dynamically and move specific authors from "Available authors" to
805 the "Chosen authors" box, and vice versa.
806
807 .. DWP screenshot!
808
809 .. figure:: graphics/chapter06/book_editform1.png
810 :alt: Screenshot of the book edit form after adding filter_horizontal.
811
812 Figure 6-13. The book edit form after adding filter_horizontal
813
814 We'd highly recommend using ``filter_horizontal`` for any ``ManyToManyField``
815 that has more than 10 items. It's far easier to use than a simple
816 multiple-select widget. Also, note you can use ``filter_horizontal``
817 for multiple fields -- just specify each name in the tuple.
818
819 ``ModelAdmin`` classes also support a ``filter_vertical`` option. This works
820 exactly as ``filter_horizontal``, but the resulting JavaScript interface stacks
821 the two boxes vertically instead of horizontally. It's a matter of personal
822 taste.
823
824 ``filter_horizontal`` and ``filter_vertical`` only work on ``ManyToManyField``
825 fields, not ``ForeignKey`` fields. By default, the admin site uses simple
826 ``<select>`` boxes for ``ForeignKey`` fields, but, as for ``ManyToManyField``,
827 sometimes you don't want to incur the overhead of having to select all the
828 related objects to display in the drop-down. For example, if our book database
829 grows to include thousands of publishers, the "Add book" form could take a
830 while to load, because it would have to load every publisher for display in the
831 ``<select>`` box.
832
833 The way to fix this is to use an option called ``raw_id_fields``. Set this to
834 a tuple of ``ForeignKey`` field names, and those fields will be displayed in
835 the admin with a simple text input box (``<input type="text">``) instead of a
836 ``<select>``. See Figure 6-14.
837
838 .. parsed-literal::
839
840 class BookAdmin(admin.ModelAdmin):
841 list_display = ('title', 'publisher', 'publication_date')
842 list_filter = ('publication_date',)
843 date_hierarchy = 'publication_date'
844 ordering = ('-publication_date',)
845 filter_horizontal = ('authors',)
846 **raw_id_fields = ('publisher',)**
847
848 .. SL Tested ok
849
850 .. DWP Screenshot!
851
852 .. figure:: graphics/chapter06/book_editform2.png
853 :alt: Screenshot of edit form after raw_id_fields.
854
855 Figure 6-14. The book edit form after adding raw_id_fields
856
857 What do you enter in this input box? The database ID of the publisher. Given
858 that humans don't normally memorize database IDs, there's also a
859 magnifying-glass icon that you can click to pull up a pop-up window, from which
860 you can select the publisher to add.
861
862 Users, Groups, and Permissions
863 ==============================
864
865 Because you're logged in as a superuser, you have access to create, edit, and
866 delete any object. Naturally, different environments require different
867 permission systems -- not everybody can or should be a superuser. Django's
868 admin site uses a permissions system that you can use to give specific users
869 access only to the portions of the interface that they need.
870
871 These user accounts are meant to be generic enough to be used outside of the
872 admin interface, but we'll just treat them as admin user accounts for now. In
873 Chapter 14, we'll cover how to integrate user accounts with the rest of your
874 site (i.e., not just the admin site).
875
876 You can edit users and permissions through the admin interface just like any
877 other object. We saw this earlier in this chapter, when we played around with
878 the User and Group sections of the admin. User objects have the standard
879 username, password, e-mail and real name fields you might expect, along with a
880 set of fields that define what the user is allowed to do in the admin
881 interface. First, there's a set of three boolean flags:
882
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
883 * The "active" flag controls whether the user is active at all.
884 If this flag is off and the user tries to log in, he won't be allowed in,
885 even with a valid password.
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
886
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
887 * The "staff" flag controls whether the user is allowed to log in to the
888 admin interface (i.e., whether that user is considered a "staff member" in
889 your organization). Since this same user system can be used to control
890 access to public (i.e., non-admin) sites (see Chapter 14), this flag
891 differentiates between public users and administrators.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
892
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
893 * The "superuser" flag gives the user full access to add, create and
894 delete any item in the admin interface. If a user has this flag set, then
895 all regular permissions (or lack thereof) are ignored for that user.
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
896
897 "Normal" admin users -- that is, active, non-superuser staff members -- are
898 granted admin access through assigned permissions. Each object editable through
899 the admin interface (e.g., books, authors, publishers) has three permissions: a
900 *create* permission, an *edit* permission and a *delete* permission. Assigning
901 permissions to a user grants the user access to do what is described by those
902 permissions.
903
904 When you create a user, that user has no permissions, and it's up to you to
905 give the user specific permissions. For example, you can give a user permission
906 to add and change publishers, but not permission to delete them. Note that
907 these permissions are defined per-model, not per-object -- so they let you say
908 "John can make changes to any book," but they don't let you say "John can make
909 changes to any book published by Apress." The latter functionality, per-object
910 permissions, is a bit more complicated and is outside the scope of this book
911 but is covered in the Django documentation.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
912
913 .. note::
914
915 Access to edit users and permissions is also controlled by this permission
916 system. If you give someone permission to edit users, she will be able to
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
917 edit her own permissions, which might not be what you want! Giving a user
918 permission to edit users is essentially turning a user into a superuser.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
919
920 You can also assign users to groups. A *group* is simply a set of permissions to
921 apply to all members of that group. Groups are useful for granting identical
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
922 permissions to a subset of users.
923
924 When and Why to Use the Admin Interface -- And When Not to
925 ==========================================================
926
927 After having worked through this chapter, you should have a good idea of how to
928 use Django's admin site. But we want to make a point of covering *when* and
929 *why* you might want to use it -- and when *not* to use it.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
930
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
931 Django's admin site especially shines when nontechnical users need to be able
932 to enter data; that's the purpose behind the feature, after all. At the
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
933 newspaper where Django was first developed, development of a typical online
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
934 feature -- say, a special report on water quality in the municipal supply --
935 would go something like this:
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
936
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
937 * The reporter responsible for the project meets with one of the developers
938 and describes the available data.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
939
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
940 * The developer designs Django models to fit this data and then opens up
941 the admin site to the reporter.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
942
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
943 * The reporter inspects the admin site to point out any missing or
944 extraneous fields -- better now than later. The developer changes the
945 models iteratively.
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
946
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
947 * When the models are agreed upon, the reporter begins entering data using
948 the admin site. At the same time, the programmer can focus on developing
949 the publicly accessible views/templates (the fun part!).
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
950
951 In other words, the raison d'être of Django's admin interface is facilitating
952 the simultaneous work of content producers and programmers.
953
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
954 However, beyond these obvious data entry tasks, the admin site is useful in a
955 few other cases:
956
fdc4800c »
2012-09-25 Fixed a bunch of reST markup errors.
957 * *Inspecting data models*: Once you've defined a few models, it can be
958 quite useful to call them up in the admin interface and enter some dummy
959 data. In some cases, this might reveal data-modeling mistakes or other
960 problems with your models.
961
962 * *Managing acquired data*: For applications that rely on data coming from
963 external sources (e.g., users or Web crawlers), the admin site gives you
964 an easy way to inspect or edit this data. You can think of it as a less
965 powerful, but more convenient, version of your database's command-line
966 utility.
967
968 * *Quick and dirty data-management apps*: You can use the admin site to
969 build yourself a very lightweight data management app -- say, to keep
970 track of expenses. If you're just building something for your own needs,
971 not for public consumption, the admin site can take you a long way. In
972 this sense, you can think of it as a beefed up, relational version of a
973 spreadsheet.
d40cfe73 »
2012-09-25 Restored *2.0* version of the book, not 1.0!
974
975 One final point we want to make clear is: the admin site is not an
976 end-all-be-all. Over the years, we've seen it hacked and chopped up to serve a
977 variety of functions it wasn't intended to serve. It's not intended to be a
978 *public* interface to data, nor is it intended to allow for sophisticated
979 sorting and searching of your data. As we said early in this chapter, it's for
980 trusted site administrators. Keeping this sweet spot in mind is the key to
981 effective admin-site usage.
acc918f9 »
2012-09-24 Initial import of djangobook from private SVN repo.
982
983 What's Next?
984 ============
985
986 So far we've created a few models and configured a top-notch interface for
987 editing data. In the `next chapter`_, we'll move on to the real "meat and potatoes"
988 of Web development: form creation and processing.
989
990 .. _next chapter: ../chapter07/
Something went wrong with that request. Please try again.