From bacbec8600d87ef2a28ab2fda447b94f5cef6960 Mon Sep 17 00:00:00 2001 From: Adrian Holovaty Date: Sat, 29 Apr 2006 02:53:35 +0000 Subject: [PATCH] magic-removal: Proofread docs/overview.txt git-svn-id: http://code.djangoproject.com/svn/django/branches/magic-removal@2787 bcc190cf-cafb-0310-a4f2-bffc1f526a37 --- docs/overview.txt | 203 ++++++++++++++++++++++++---------------------- 1 file changed, 104 insertions(+), 99 deletions(-) diff --git a/docs/overview.txt b/docs/overview.txt index 4e8c3bc6c9..544a897ac6 100644 --- a/docs/overview.txt +++ b/docs/overview.txt @@ -16,34 +16,39 @@ to start a project. Design your model ================= -Start by describing your database layout in Python code. Django's data-model API -offers many rich ways of representing your models -- so far, it's been -solving two years' worth of database-schema problems. Here's a quick example:: +Although you can use Django without a database, it comes with an +object-relational mapper in which you describe your database layout in Python +code. - class Reporter(meta.Model): - full_name = meta.CharField(maxlength=70) +The data-model syntax offers many rich ways of representing your models -- so +far, it's been solving two years' worth of database-schema problems. Here's a +quick example:: - def __repr__(self): + class Reporter(models.Model): + full_name = models.CharField(maxlength=70) + + def __str__(self): return self.full_name - class Article(meta.Model): - pub_date = meta.DateTimeField() - headline = meta.CharField(maxlength=200) - article = meta.TextField() - reporter = meta.ForeignKey(Reporter) + class Article(models.Model): + pub_date = models.DateTimeField() + headline = models.CharField(maxlength=200) + article = models.TextField() + reporter = models.ForeignKey(Reporter) - def __repr__(self): + def __str__(self): return self.headline Install it ========== -Next, run the Django command-line utility. It'll create the database tables for -you automatically, in the database specified in your Django settings. Django -works best with PostgreSQL, although we've recently added beta MySQL -support and other database adapters are on the way:: +Next, run the Django command-line utility to create the database tables +automatically:: - django-admin.py install news + manage.py syncdb + +The ``syncdb`` command looks at all your available models and creates tables +in your database for whichever tables don't already exist. Enjoy the free API ================== @@ -51,16 +56,14 @@ Enjoy the free API With that, you've got a free, and rich, Python API to access your data. The API is created on the fly: No code generation necessary:: - # Modules are dynamically created within django.models. - # Their names are plural versions of the model class names. - >>> from django.models.news import reporters, articles + >>> from mysite.models import Reporter, Article # No reporters are in the system yet. - >>> reporters.get_list() + >>> Reporter.objects.all() [] # Create a new Reporter. - >>> r = reporters.Reporter(full_name='John Smith') + >>> r = Reporter(full_name='John Smith') # Save the object into the database. You have to call save() explicitly. >>> r.save() @@ -70,52 +73,48 @@ is created on the fly: No code generation necessary:: 1 # Now the new reporter is in the database. - >>> reporters.get_list() + >>> Reporter.objects.all() [John Smith] # Fields are represented as attributes on the Python object. >>> r.full_name 'John Smith' - # Django provides a rich database lookup API that's entirely driven by keyword arguments. - >>> reporters.get_object(id__exact=1) + # Django provides a rich database lookup API. + >>> Reporter.objects.get(id=1) John Smith - >>> reporters.get_object(full_name__startswith='John') + >>> Reporter.objects.get(full_name__startswith='John') John Smith - >>> reporters.get_object(full_name__contains='mith') + >>> Reporter.objects.get(full_name__contains='mith') John Smith - >>> reporters.get_object(id__exact=2) + >>> Reporter.objects.get(id=2) Traceback (most recent call last): ... - django.models.news.ReporterDoesNotExist: Reporter does not exist for {'id__exact': 2} - - # Lookup by a primary key is the most common case, so Django provides a - # shortcut for primary-key exact lookups. - # The following is identical to reporters.get_object(id__exact=1). - >>> reporters.get_object(pk=1) - John Smith + DoesNotExist: Reporter does not exist for {'id__exact': 2} # Create an article. >>> from datetime import datetime - >>> a = articles.Article(pub_date=datetime.now(), headline='Django is cool', article='Yeah.', reporter_id=1) + >>> a = Article(pub_date=datetime.now(), headline='Django is cool', + ... article='Yeah.', reporter=r) >>> a.save() # Now the article is in the database. - >>> articles.get_list() + >>> Article.objects.all() [Django is cool] # Article objects get API access to related Reporter objects. - >>> r = a.get_reporter() + >>> r = a.reporter >>> r.full_name 'John Smith' # And vice versa: Reporter objects get API access to Article objects. - >>> r.get_article_list() + >>> r.article_set.all() [Django is cool] - # The API follows relationships as far as you need. - # Find all articles by a reporter whose name starts with "John". - >>> articles.get_list(reporter__full_name__startswith="John") + # The API follows relationships as far as you need, performing efficient + # JOINs for you behind the scenes. + # This finds all articles by a reporter whose name starts with "John". + >>> Article.objects.filter(reporter__full_name__startswith="John") [Django is cool] # Change an object by altering its attributes and calling save(). @@ -128,61 +127,64 @@ is created on the fly: No code generation necessary:: A dynamic admin interface: It's not just scaffolding -- it's the whole house ============================================================================ -Once your models are defined, Django can automatically create an administrative -interface -- a Web site that lets authenticated users add, change and -delete objects. It's as easy as adding an extra ``admin`` attribute to your -model classes:: +Once your models are defined, Django can automatically create a professional, +production ready administrative interface -- a Web site that lets authenticated +users add, change and delete objects. It's as easy as adding a line of code to +your model classes:: - class Article(meta.Model): - pub_date = meta.DateTimeField() - headline = meta.CharField(maxlength=200) - article = meta.TextField() - reporter = meta.ForeignKey(Reporter) - class Meta: - admin = meta.Admin() + class Article(models.Model): + pub_date = models.DateTimeField() + headline = models.CharField(maxlength=200) + article = models.TextField() + reporter = models.ForeignKey(Reporter) + class Admin: pass The philosophy here is that your site is edited by a staff, or a client, or maybe just you -- and you don't want to have to deal with creating backend interfaces just to manage content. -Our typical workflow at World Online is to create models and get the admin sites -up and running as fast as possible, so our staff journalists can start -populating data. Then we develop the way data is presented to the public. +One typical workflow in creating Django apps is to create models and get the +admin sites up and running as fast as possible, so your staff (or clients) can +start populating data. Then, develop the way data is presented to the public. Design your URLs ================ A clean, elegant URL scheme is an important detail in a high-quality Web -application. Django lets you design URLs however you want, with no framework -limitations. +application. Django encourages beautiful URL design and doesn't put any cruft +in URLs, like ``.php`` or ``.asp``. -To design URLs for an app, you create a Python module. For the above -Reporter/Article example, here's what that might look like:: +To design URLs for an app, you create a Python module called a URLconf. A table +of contents for your app, it contains a simple mapping between URL patterns and +Python callback functions. URLconfs also serve to decouple URLs from Python +code. + +Here's what a URLconf might look like for the above ``Reporter``/``Article`` +example above:: from django.conf.urls.defaults import * urlpatterns = patterns('', - (r'^/articles/(?P\d{4})/$', 'myproject.news.views.year_archive'), - (r'^/articles/(?P\d{4})/(?P\d{2})/$', 'myproject.news.views.month_archive'), - (r'^/articles/(?P\d{4})/(?P\d{2})/(?P\d+)/$', 'myproject.news.views.article_detail'), + (r'^/articles/(\d{4})/$', 'mysite.views.year_archive'), + (r'^/articles/(\d{4})/(\d{2})/$', 'mysite.views.month_archive'), + (r'^/articles/(\d{4})/(\d{2})/(\d+)/$', 'mysite.views.article_detail'), ) -The code above maps URLs, as regular expressions, to the location of Python -callback functions (views). The regular expressions use parenthesis to "capture" -values from the URLs. When a user requests a page, Django runs through each -regular expression, in order, and stops at the first one that matches the -requested URL. (If none of them matches, Django calls a special 404 view.) This -is blazingly fast, because the regular expressions are compiled at load time. +The code above maps URLs, as simple regular expressions, to the location of +Python callback functions ("views"). The regular expressions use parenthesis to +"capture" values from the URLs. When a user requests a page, Django runs +through each pattern, in order, and stops at the first one that matches the +requested URL. (If none of them matches, Django calls a special-case 404 view.) +This is blazingly fast, because the regular expressions are compiled at load +time. Once one of the regexes matches, Django imports and calls the given view, which is a simple Python function. Each view gets passed a request object -- -which contains request metadata and lets you access GET and POST data as simple -dictionaries -- and the values captured in the regex, via keyword -arguments. +which contains request metadata -- and the values captured in the regex. For example, if a user requested the URL "/articles/2005/05/39323/", Django would call the function ``myproject.news.views.article_detail(request, -year='2005', month='05', article_id='39323')``. +'2005', '05', '39323')``. Write your views ================ @@ -193,29 +195,29 @@ raising an exception such as ``Http404``. The rest is up to you. Generally, a view retrieves data according to the parameters, loads a template and renders the template with the retrieved data. Here's an example view for -article_detail from above:: +``year_archive`` from above:: - def article_detail(request, year, month, article_id): - # Use the Django API to find an object matching the URL criteria. - a = get_object_or_404(articles, pub_date__year=year, pub_date__month=month, pk=article_id) - return render_to_response('news/article_detail.html', {'article': a}) + def year_archive(request, year): + a_list = Article.objects.filter(pub_date__year=year) + return render_to_response('news/year_archive.html', {'article_list': a_list}) -This example uses Django's template system, which has several key features. +This example uses Django's template system, which has several powerful +features but strives to stay simple enough for non-programmers to use. Design your templates ===================== -The code above loads the ``news/article_detail`` template. +The code above loads the ``news/year_archive.html`` template. Django has a template search path, which allows you to minimize redundancy among templates. In your Django settings, you specify a list of directories to check for templates. If a template doesn't exist in the first directory, it checks the second, and so on. -Let's say the ``news/article_detail`` template was found. Here's what that might -look like:: +Let's say the ``news/article_detail.html`` template was found. Here's what that +might look like:: - {% extends "base" %} + {% extends "base.html" %} {% block title %}{{ article.headline }}{% endblock %} @@ -226,12 +228,10 @@ look like:: {{ article.article }} {% endblock %} - -It should look straightforward. Variables are surrounded by double-curly braces. -``{{ article.headline }}`` means "Output the value of the article's headline -attribute." But dots aren't used only for attribute lookup: They also can do -dictionary-key lookup, index lookup and function calls (as is the case with -``article.get_reporter``). +Variables are surrounded by double-curly braces. ``{{ article.headline }}`` +means "Output the value of the article's headline attribute." But dots aren't +used only for attribute lookup: They also can do dictionary-key lookup, index +lookup and function calls (as is the case with ``article.get_reporter``). Note ``{{ article.pub_date|date:"F j, Y" }}`` uses a Unix-style "pipe" (the "|" character). This is called a template filter, and it's a way to filter the value @@ -243,13 +243,13 @@ You can chain together as many filters as you'd like. You can write custom filters. You can write custom template tags, which run custom Python code behind the scenes. -Finally, Django uses the concept of template inheritance: That's what the ``{% -extends "base" %}`` does. It means "First load the template called 'base', which -has defined a bunch of blocks, and fill the blocks with the following blocks." -In short, that lets you dramatically cut down on redundancy in templates: Each -template has to define only what's unique to that template. +Finally, Django uses the concept of "template inheritance": That's what the +``{% extends "base.html" %}`` does. It means "First load the template called +'base', which has defined a bunch of blocks, and fill the blocks with the +following blocks." In short, that lets you dramatically cut down on redundancy +in templates: Each template has to define only what's unique to that template. -Here's what the "base" template might look like:: +Here's what the "base.html" template might look like:: @@ -265,13 +265,18 @@ Simplistically, it defines the look-and-feel of the site (with the site's logo), and provides "holes" for child templates to fill. This makes a site redesign as easy as changing a single file -- the base template. +It also lets you create multiple versions of a site, with different base +templates, while reusing child templates. Django's creators have used this +technique to create strikingly different cell-phone editions of sites -- simply +by creating a new base template. + Note that you don't have to use Django's template system if you prefer another system. While Django's template system is particularly well-integrated with Django's model layer, nothing forces you to use it. For that matter, you don't -have to use Django's API, either. You can use another database abstraction -layer, you can read XML files, you can read files off disk, or anything you -want. Each piece of Django -- models, views, templates -- is decoupled -from the next. +have to use Django's database API, either. You can use another database +abstraction layer, you can read XML files, you can read files off disk, or +anything you want. Each piece of Django -- models, views, templates -- is +decoupled from the next. This is just the surface ========================