[Django][The Polls][Chap 0] URL과 View Binding & PostgreSQL 연동

Info Notice:
안녕하세요. HwanSeok입니다. The Polls 프로젝트는 docs.djangoproject.com를 참조하여 진행됩니다. 본 포스팅은 전체적인 개발 흐름과 The Polls 프로젝트를 효과적으로 이해하기 위한 설명이 포함되어 있습니다.

결과

제일 먼저 현재까지 진행된 결과부터 보겠습니다.

/polls

/polls로 접속하면 아래와 같은 HttpResponse를 볼 수 있습니다.

chapter-0-3

/admin

/admin로 접속하면 아래와 같은 화면을 볼 수 있습니다.

django를 통해 The Polls 프로젝트의 admin 사이트를 구축하였고, The Polls에 등록된 Polls App을 볼 수 있습니다. 오른쪽에는 제가 최근에 진행한 Action의 List를 볼 수 있습니다.

chapter-0-0

POLLS의 Questions를 클릭하면 아래와 같은 모습입니다.

chapter-0-1

생성된 Questions의 객체가 리스트로 보여집니다. 클릭하면 Question 객체의 Fields를 볼 수 있습니다.

chapter-0-2

Question 객체는 두 가지 Fields를 가지고 객체의 값을 확인/수정/저장 할 수 있습니다.

진행사항

프로젝트 생성 및 실행 확인

먼저 프로젝트를 생성합니다.

1
django-admin startproject mysite

Django 프로젝트가 제대로 동작하는지 확인하기 위해 개발 서버를 실행했습니다.

1
2
3
py manage.py runserver
또는
py manage.py runserver 8000

runserver는 요청이 들어올 때마다 자동으로 python 코드를 다시 불러옵니다. 대부분의 코드 변경사항을 page reload시 자동으로 적용됩니다.

설문조사 앱 만들기

Info Notice:
project와 app의 상관관계
app은 특정 역할을 수행하는 web application입니다. project는 특정 website를 위한 apps와 configs의 집합입니다.
The Polls project는 두 개의 app을 가지고 있습니다. 프로젝트 생성시 기본으로 생성되는 (다른 앱의 기준이 되는)mysite 앱과 poll의 기능을 위한 polls 앱이 있습니다. polls app은 mysite app에 등록되어서 사용됩니다.

설문조사 앱을 만듭니다.

1
py manage.py startapp polls

아래와 같은 tree가 생성됩니다.

1
2
3
4
5
6
7
8
9
10
polls/
    __init__.py
    admin.py
    apps.py
    migrations/
        __init__.py
    models.py
    tests.py
    urls.py
    views.py

뷰 생성 및 URL 연결

polls/view.py에 아래와 같이 작성합니다.

1
2
3
4
5
from django.http import HttpResponse


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

view를 호출하기 위해서는 연결된 url이 필요하고 url을 설정하기 위해서 urlconf를 사용합니다. 현재 프로젝트에는 mysite, polls 두 개의 app이 있습니다. 그리고 각 app은 urlconf를 위한 /urls.py를 가지고 있습니다.

  • polls/urls.py
    1
    2
    3
    4
    5
    6
    7
    
    from django.urls import path
    
    from . import views
    
    urlpatterns = [
        path('', views.index, name='index'),
    ]
    
  • mysite/urls.py
    1
    2
    3
    4
    5
    6
    7
    
    from django.contrib import admin
    from django.urls import include, path
    
    urlpatterns = [
        path('polls/', include('polls.urls')),
        path('admin/', admin.site.urls),
    ]
    

polls/urls.py는 polls/view.py에서 생성한 index view를 ‘/’ 경로와 binding 하는 역할을 수행합니다. ‘polls/’ 경로와 polls/urls.py를 binding하는 역할을 수행합니다. path('admin/', admin.site.urls)는 project의 중심이 되는 app에 존재하는 default 값입니다. mysite/urls.py가 polls/urls.py를 참조할 수 있도록 해주는 것은 include()의 역할입니다.

index라는 이름의 polls의 view가 mysite에 연결되었으니 실행해서 확인합니다.

1
py manage.py runserver

chapter-0-3

Success Notice: 즉, 위 모습은 url와 view를 적절히 binding한 결과로 보여지는 것입니다. :+1:

데이터베이스 설치 및 연동

python이 내부적으로 sqlite3를 지원하지만, 저는 PostgreSQL을 사용했습니다. 단순히 사용해보고 싶어서 선택한 것입니다.(mysql과의 차이점은 추후 포스팅하겠습니다.) PostresSQL 연동은 여기에서 많은 도움을 받았습니다.

  1. PostgreSQL 다운로드 및 PostgreSQL Root 계정 생성
  2. 데이터 베이스 생성
    1
    
      CREATE DATABASE 데이터베이스 이름;
    
  3. 위에서 생성한 데이터베이스를 관리할 user, password 지정
    1
    
      CREATE USER user_id WITH PASSWORD 'password';
    
  4. 인코딩, isolation, timezone 설정
    1
    2
    3
    
      $ ALTER ROLE user_id SET client_encoding TO 'utf8'; 
      $ ALTER ROLE user_id SET default_transaction_isolation TO 'read committed'; 
      $ ALTER ROLE user_id SET TIME ZONE 'Asia/Seoul';
    
  5. USER에게 데이터베이스 접근 권한 주기
    1
    
      GRANT ALL PRIVILEGES ON DATABASE 데이터베이스  To user_id;
    
  6. /mysite/setting.py Database 편집
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    
      DATABASES = {
       'default': {
           'ENGINE': 'django.db.backends.postgresql',
           'NAME': 'mysite',
           'USER': '******',
           'PASSWORD': '******',
           'HOST': 'localhost',
           'PORT': '',
       }
      }
    
  7. mysite/settings.py Timezone 편집
    1
    
      TIME_ZONE = 'Asia/Seoul'  
    

Django default apps migration

기본제공되는 앱들은 아래와 같은 역할을 수행합니다.

  • django.contrib.admin – 관리용 사이트. 곧 사용하게 될 겁니다.
  • django.contrib.auth – 인증 시스템.
  • django.contrib.contenttypes – 컨텐츠 타입을 위한 프레임워크.
  • django.contrib.sessions – 세션 프레임워크.
  • django.contrib.messages – 메세징 프레임워크.
  • django.contrib.staticfiles – 정적 파일을 관리하는 프레임워크.

커스텀 앱을 migration하기 전에 기본 앱부터 migration을 수행해줍니다.

Info Notice:
DataBase Migration이란?
본 포스팅에서 사용되는 Migration은 DB Migration을 의미합니다. 이것은 개별 SQL 파일을 consol에서 직접 실행하지 않고 프레임워크의 명령어를 통해서 실행하고, 이 결과를 별도의 table에 버전관리하는 기법을 말합니다.

1
py manage.py migrate

Polls app migration

먼저 두개의 모델을 생성했습니다.

1
2
3
4
5
6
7
8
9
10
11
12
13
# polls/models.py
from django.db import models


class Question(models.Model):
    question_text = models.CharField(max_length=200)
    pub_date = models.DateTimeField('date published')


class Choice(models.Model):
    question = models.ForeignKey(Question, on_delete=models.CASCADE)
    choice_text = models.CharField(max_length=200)
    votes = models.IntegerField(default=0)

그리고 polls 앱을 mysite에 등록했습니다. 경로.경로.클래스이름을 사용합니다.

1
2
3
4
5
6
7
# 참고 
# polls/app.js
from django.apps import AppConfig


class PollsConfig(AppConfig):
    name = 'polls'
1
2
3
4
5
6
7
8
9
INSTALLED_APPS = [
    'polls.apps.PollsConfig',
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
]

migration에 포함할 모델의 변경사항을 파일로 저장하고,

1
py manage.py makemigrations polls
1
2
3
4
5
# 결과
Migrations for 'polls':
polls/migrations/0001_initial.py
  - Create model Question
  - Create model Choice

sqlmmigrate로 migrate 입력시 실행될 command 확인합니다.

1
py manage.py sqlmigrate polls 0001
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
BEGIN;
--
-- Create model Question
--
CREATE TABLE "polls_question" (
    "id" serial NOT NULL PRIMARY KEY,
    "question_text" varchar(200) NOT NULL,
    "pub_date" timestamp with time zone NOT NULL
);
--
-- Create model Choice
--
CREATE TABLE "polls_choice" (
    "id" serial NOT NULL PRIMARY KEY,
    "choice_text" varchar(200) NOT NULL,
    "votes" integer NOT NULL,
    "question_id" integer NOT NULL
);
ALTER TABLE "polls_choice"
  ADD CONSTRAINT "polls_choice_question_id_c5b4b260_fk_polls_question_id"
    FOREIGN KEY ("question_id")
    REFERENCES "polls_question" ("id")
    DEFERRABLE INITIALLY DEFERRED;
CREATE INDEX "polls_choice_question_id_c5b4b260" ON "polls_choice" ("question_id");

COMMIT;

마지막으로 migration 실행하면 위 DB에 적용됩니다.

1
py manage.py migrate

API 가지고 놀기

이 부분은 여기를 그대로 따라하는 것이기 때문에 본문의 내용을 옮겨적지 않습니다.

이렇게 쉘에서 객체를 생성할 수 있고, 또 객체가 DB에 저장되는 것은 장고가 기본적으로 제공하는 API를 사용할 수 있기 때문입니다.

여기까지 진행하고 dbeaver를 설치해서 postgreSQL을 gui로 확인해보면 아래와 같이 나옵니다.

chapter-1-4

dbeaver를 설치하고 mysite/settings.py의 아래 부분에서 입력한 정보로 connection을 생성해주면 됩니다.

1
2
3
4
5
6
7
8
9
10
DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.postgresql',
        'NAME': 'mysite',
        'USER': ''************',',
        'PASSWORD': '************',
        'HOST': 'localhost',
        'PORT': '',
    }
}

관리자 생성하기

  1. 슈퍼계정 생성
    1
    
      py manage.py createsuperuser
    
  2. 개발 서버 시작
    1
    
      py manage.py runserver
    
  3. localhost:8000/admin에 접속
    • poll app이 보이지 않는 문제점이 존재
  4. 마지막으로 admin 사이트에서 poll app을 변경 가능하도록 수정합니다.
    1
    2
    3
    4
    5
    6
    
     # polls/admmin.py  
     from django.contrib import admin
    
     from .models import Question
    
     admin.site.register(Question)
    

Success Notice: 위와 같은 과정을 거쳐 처음에 보았던 결과 페이지를 생성하였습니다. 수고하셨습니다. :+1:

개발환경

  • window 10
  • python 3.6.8
  • django 3.1.5

Leave a comment