Tuesday, January 31, 2012

Python & Django - Creating models

Creating models

Now that your environment -- a "project" -- is set up, you're set to start doing work.
Each application you write in Django consists of a Python package, somewhere on your Python path, that follows a certain convention. Django comes with a utility that automatically generates the basic directory structure of an app, so you can focus on writing code rather than creating directories.
Projects vs. apps
What's the difference between a project and an app? An app is a Web application that does something -- e.g., a Weblog system, a database of public records or a simple poll app. A project is a collection of configuration and apps for a particular Web site. A project can contain multiple apps. An app can be in multiple projects.
Your apps can live anywhere on your Python path. In this tutorial, we'll create our poll app in the mysitedirectory for simplicity.
To create your app, make sure you're in the mysite directory and type this command:
python manage.py startapp polls
That'll create a directory polls, which is laid out like this:
polls/
    __init__.py
    models.py
    tests.py
    views.py
This directory structure will house the poll application.
The first step in writing a database Web app in Django is to define your models -- essentially, your database layout, with additional metadata.
Philosophy
A model is the single, definitive source of data about your data. It contains the essential fields and behaviors of the data you're storing. Django follows the DRY Principle. The goal is to define your data model in one place and automatically derive things from it.
In our simple poll app, we'll create two models: polls and choices. A poll has a question and a publication date. A choice has two fields: the text of the choice and a vote tally. Each choice is associated with a poll.
These concepts are represented by simple Python classes. Edit the polls/models.py file so it looks like this:
from django.db import models
 
class Poll(models.Model):
    question = models.CharField(max_length=200)
    pub_date = models.DateTimeField('date published')
 
class Choice(models.Model):
    poll = models.ForeignKey(Poll)
    choice = models.CharField(max_length=200)
    votes = models.IntegerField()
The code is straightforward. Each model is represented by a class that subclassesdjango.db.models.Model. Each model has a number of class variables, each of which represents a database field in the model.
Each field is represented by an instance of a Field class -- e.g., CharField for character fields andDateTimeField for datetimes. This tells Django what type of data each field holds.
The name of each Field instance (e.g. question or pub_date ) is the field's name, in machine-friendly format. You'll use this value in your Python code, and your database will use it as the column name.
You can use an optional first positional argument to a Field to designate a human-readable name. That's used in a couple of introspective parts of Django, and it doubles as documentation. If this field isn't provided, Django will use the machine-readable name. In this example, we've only defined a human-readable name for Poll.pub_date. For all other fields in this model, the field's machine-readable name will suffice as its human-readable name.
Some Field classes have required elements. CharField, for example, requires that you give it amax_length. That's used not only in the database schema, but in validation, as we'll soon see.
Finally, note a relationship is defined, using ForeignKey. That tells Django each Choice is related to a single Poll. Django supports all the common database relationships: many-to-ones, many-to-manys and one-to-ones.
For the minimalists
Like we said above, the default applications are included for the common case, but not everybody needs them. If you don't need any or all of them, feel free to comment-out or delete the appropriate line(s) from INSTALLED_APPS before running syncdb. The syncdbcommand will only create tables for apps in INSTALLED_APPS.

No comments: