You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 14 Next »

For your information, this documentation is re-created based on https://docs.djangoproject.com/en/2.1/intro/ for my reference.

Let us create a Python application for "online poll" based on Django. The first thing you should do is changing your working directory to your project.

$ cd my_project


STEP 1. Create an application

In order to create an app, you will need "manage.py" created by Django. Once you verify it, you can create "online poll" app by running below command.

$ python manage.py startapp polls


You will be able to see the directory structure like below if you haven't faced any error

polls/
    __init__.py
    admin.py
    apps.py
    migrations/
        __init__.py
    models.py
    tests.py
    views.py

So above directory will be your base camp for "online poll" application.

Creating a first view

Let us open views.py and add some codes like below.

polls/views.py
from django.shortcuts import render

# Create your views here.
from django.http import HttpResponse


def index(request):
    return HttpResponse("Hello, world. You're at the polls index.")

The above is the most simple example of view in Django. In order to call view, you should use URLconf in order to have the connected URL. What you should do is just creating a null file as urls.py. You can do it like below

$ touch urls.py

Then you should be able to see your directory structure like below

polls/
    __init__.py
    admin.py
    apps.py
    migrations/
        __init__.py
    models.py
    tests.py
    urls.py
    views.py

And let us put below content to urls.py

polls/urls.py
from django.urls import path

from . import views

urlpatterns = [
    path('', views.index, name='index'),
]

The next action you should do is adding following two lines to url.py on your project like below.

/urls.py
from django.conf.urls import include


/urls.py
path('polls/', include('polls.urls')),

So, the final code should be like below

/urls.py
from django.contrib import admin
from django.urls import include, path
from django.conf.urls import include


urlpatterns = [
    path('admin/', admin.site.urls),
    path('polls/', include('polls.urls')),
]

Now index view is integrated with URLconf. Time for you to check your server by following command like

$ python manage.py runserver

If you face an error like below, you should check if your python is properly installed and django is running on virtual environment like I mentioned at "1. How do I setup Django development environment on Mac?" or not.


STEP 2. Database setup

If everything goes fine, now is time for us to setup a database where can store poll results. Let us do it step by step.

  1. Open up settings.py on your project, and you can see the default database settings like below

    settings.py
    # Database
    # https://docs.djangoproject.com/en/2.1/ref/settings/#databases
    
    
    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.sqlite3',
            'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
        }
    }

    If you want to use mysql instead of sqlite3, you can use it by replacing as "django.db.backends.mysql". For oracle, it will be "django.db.backends.oracle". 
    If you are not using SQLite as your database, additional settings such as USER, PASSWORD, and HOST must be added. For more details, see the reference documentation for DATABASES.
    Example)

    settings.py
    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.postgresql',
            'USER': 'mydatabaseuser',
            'NAME': 'mydatabase',
            'TEST': {
                'NAME': 'mytestdatabase',
            },
        },
    }


    Once you set all your requirements, you should run following command.

    python manage.py migrate
  2. Creating models for online poll.

    In our simple poll app, we’ll create two models: Question and Choice. A Question 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 Question.

    These concepts are represented by simple Python classes. Edit the polls/models.py file so it looks like this:

    polls/models.py
    from django.db import models
    
    # Create your models here.
    class Question(models.Model):
        question_text = models.CharField(max_length=200)
        pub_date = models.DateTimeField('date published')
        def __str__(self):
            return self.question_text
    
    class Choice(models.Model):
        question = models.ForeignKey(Question, on_delete=models.CASCADE)
        choice_text = models.CharField(max_length=200)
        votes = models.IntegerField(default=0)
        def __str__(self):
            return self.choice_text

    If you see above, it looks like a table schema when we create a table in database. I won't elaborate the detail about above for this time.

  3. Activating models
    Even though we have created an app at the moment, but actually we can't say "polls" are correctly integrated with the project. In django, we should make some additional action to make it happen.
    To include the app in our project, we need to add a reference to its configuration class in the INSTALLED_APPS setting. The PollsConfig class is in the polls/apps.py file,

    polls/apps.py
    from django.apps import AppConfig
    
    class PollsConfig(AppConfig):
        name = 'polls'


    so its dotted path is 'polls.apps.PollsConfig'. Edit the <your project folder>/settings.py file and add that dotted path to the INSTALLED_APPS setting. It’ll look like this:

    <your project folder>/settings.py
    INSTALLED_APPS = [
        'polls.apps.PollsConfig',
        'django.contrib.admin',
        'django.contrib.auth',
        'django.contrib.contenttypes',
        'django.contrib.sessions',
        'django.contrib.messages',
        'django.contrib.staticfiles',
    ]

    Note that 'polls.apps.PollsConfig' is added on top of 'django.contrib.admin'.

    Now Django knows to include the polls app. Let’s run another command:

    python manage.py makemigrations polls

    As a result, you should see similar to the following

    Migrations for 'polls':
      polls/migrations/0001_initial.py
        - Create model Choice
        - Create model Question
        - Add field question to choice

    By running makemigrations, you’re telling Django that you’ve made some changes to your models (in this case, you’ve made new ones) and that you’d like the changes to be stored as a migration.

    Migrations are how Django stores changes to your models (and thus your database schema) - they’re just files on disk. You can read the migration for your new model if you like; it’s the file polls/migrations/0001_initial.py. Don’t worry, you’re not expected to read them every time Django makes one, but they’re designed to be human-editable in case you want to manually tweak how Django changes things.

    There’s a command that will run the migrations for you and manage your database schema automatically - that’s called migrate, and we’ll come to it in a moment - but first, let’s see what SQL that migration would run. The sqlmigrate command takes migration names and returns their SQL:

    python manage.py sqlmigrate polls 0001

    As a result, you should see similar to the following

    BEGIN;
    --
    -- Create model Choice
    --
    CREATE TABLE "polls_choice" ("id" integer NOT NULL PRIMARY KEY AUTOINCREMENT, "choice_text" varchar(200) NOT NULL, "votes" integer NOT NULL);
    --
    -- Create model Question
    --
    CREATE TABLE "polls_question" ("id" integer NOT NULL PRIMARY KEY AUTOINCREMENT, "question_text" varchar(200) NOT NULL, "pub_date" datetime NOT NULL);
    --
    -- Add field question to choice
    --
    ALTER TABLE "polls_choice" RENAME TO "polls_choice__old";
    CREATE TABLE "polls_choice" ("id" integer NOT NULL PRIMARY KEY AUTOINCREMENT, "choice_text" varchar(200) NOT NULL, "votes" integer NOT NULL, "question_id" integer NOT NULL REFERENCES "polls_question" ("id") DEFERRABLE INITIALLY DEFERRED);
    INSERT INTO "polls_choice" ("id", "choice_text", "votes", "question_id") SELECT "id", "choice_text", "votes", NULL FROM "polls_choice__old";
    DROP TABLE "polls_choice__old";
    CREATE INDEX "polls_choice_question_id_c5b4b260" ON "polls_choice" ("question_id");
    COMMIT;

    Now, run migrate again to create those model tables in your database:

    python manage.py migrate

    You will see following similar results if everything goes fine.

    Operations to perform:
      Apply all migrations: admin, auth, contenttypes, polls, sessions
    Running migrations:
      Applying polls.0001_initial... OK

    But for now, remember the three-step guide to making model changes:

    1. Change your models (in models.py).

    2. Run python manage.py makemigrations to create migrations for those changes

    3. Run python manage.py migrate to apply those changes to the database.

  4. Playing with the API
    Now, let’s hop into the interactive Python shell and play around with the free API Django gives you. To invoke the Python shell, use this command:

    python manage.py shell

    Once you’re in the shell, explore the database API:

    >>> from polls.models import Choice, Question
    >>> Question.objects.all()
    <QuerySet []>
    >>> from django.utils import timezone
    >>> q = Question(question_text="What's new?", pub_date=timezone.now())
    >>> q.save()
    >>> q.id
    1
    >>> q.question_text
    "What's new?"
    >>> q.pub_date
    datetime.datetime(2018, 11, 10, 5, 29, 23, 419109, tzinfo=<UTC>)
    >>> q.question_text = "What's up?"
    >>> q.save()
    >>> Question.objects.all()
    <QuerySet [<Question: Question object (1)>]>

    If everything is okay, you will see the same result except q.pub_date, because that will be based on your current timezone.

  • No labels