DjangoでTodoアプリを作る①Dockerで環境を構築する

#はじめに
チュートリアルの代表格であるTodoアプリをDjangoで作ってみました。
コードの意味などでっっきる限り細かく丁寧に書いたつもりです。

※もし、間違いなどあればご指摘ください！:bow:

##対象者
djangoに入門したい方

##記事一覧
[DjangoでTodoアプリを作る①Dockerで環境を構築する](https://qiita.com/takos/items/b9ba0b60c6f71b428aac)
[DjangoでTodoアプリを作る②フォルダ一覧ページの作成](https://qiita.com/takos/items/3e480183e72f41b69b84)
[DjangoでTodoアプリを作る③タスク一覧ページの作成](https://qiita.com/takos/items/828283aad5e5e2d8573d)
[DjangoでTodoアプリを作る④フォルダー、タスク作成機能の実装](https://qiita.com/takos/items/ce580c5781956a7c7eba)
[DjangoでTodoアプリを作る⑤タスク編集機能の作成](https://qiita.com/takos/items/dc4b91784cf895cc71c3)

##完成図
- トップページ
![トップページ改.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/370196/3f383d9c-eef1-7466-4862-5480a0f07286.png)

- フォルダ作成ページ
![フォルダー作成機能.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/370196/2d9f44e4-fef7-93ea-f38f-51abadf0133b.png)

- タスク作成ページ
![タスク作成機能.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/370196/561065ea-c841-2842-db96-4f2be74049cb.png)

- タスク編集ページ
![タスク編集ページ.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/370196/00e48df3-b8d2-b916-e63f-4ec253e1c28c.png)



##機能一覧
- タスク作成機能
- タスク編集機能
- タスク一覧表示
- フォルダ作成機能
- フォルダ一覧表示

大きく機能を分類するとこんな感じです！
では、作っていきます！

#Dockerで開発環境構築
以下のディレクトリ構成を作成していきます。

```  
django_todo
├── docker-compose.yml
├── dockerfile
├── manage.py
├── requirements.txt
└── django_todo
    ├── __init__.py
    ├── __pycache__
    │   ├── __init__.cpython-38.pyc
    │   ├── settings.cpython-38.pyc
    │   ├── urls.cpython-38.pyc
    │   └── wsgi.cpython-38.pyc
    ├── settings.py
    ├── urls.py
    └── wsgi.py
```

**1.作業ディレクトリの作成**

```
$ mkdir django_todo
$ cd django_todo
```  


**2.dockerファイル, requirements.txtを作る**
django_todoディレクトリ配下にDockerfileとdocker-compose.ymlとrequirements.txtを作成します。

```
$ touch Dockerfile docker-compose.yml requirements.txt
```
  

**3.Dockerfile**
Dockerfile, docker-compose.yml, requirements.txt に以下のように記述します。

```Dockerfile:Dockerfile

# ベースとなるイメージを指定
FROM python:3
# バッファにデータを保持しない設定(1でなくても任意の文字でいい)
ENV PYTHONUNBUFFERED 1
# コンテナの中にディレクトリを作成
RUN mkdir /code
# 作業ディレクトリを指定
WORKDIR /code
COPY requirements.txt /code/
RUN pip install -r requirements.txt
COPY . /code/
```

```Docker-compose.yml
# ymlファイルのバージョン指定
version: '3'
# コンテナを定義
services:
    web:
        # Dockerfileをビルド
        build: .
        command: python3 manage.py runserver 0.0.0.0:8000
        # マウント場所の指定
        volumes:
            - .:/code
        ports:
            - "8000:8000"
        # dbサービスが立ち上がってから起動するように指定
        depends_on:
            - db
    db:
        image: postgres
        ports: 
            - "5432"
        environment:
          - POSTGRES_DB=postgres
          - POSTGRES_USER=postgres
          - POSTGRES_PASSWORD=postgres
 ```

```requirements.txt
Django>=2.0,<3.0
psycopg2>=2.7,<3.0
```
requirements.txtを記述することによって、記述したパッケージを指定したバージョンで一括インストールすることができます。


**4.Djangoプロジェクトの作成**

```
$ docker-compose run web django-admin.py startproject django_todo .
```
これは Compose に対して、コンテナ内で django-admin.py startproject django_todo を実行するよう命令しています。
これによりディレクトリ構成が以下のようになります。

```
django_todo
├── Dockerfile
├── django_todo
│   ├── __init__.py
│   ├── settings.py
│   ├── urls.py
│   └── wsgi.py
├── docker-compose.yml
├── manage.py
└── requirements.txt

```

**5.データベースの設定**
データベースはpostgresqlを利用します。
データベースを設定するために、django_todo/setting.pyを編集していきます。
DATABASES = ...
ALLOWED_HOSTS =...
 を以下のものに変更する。

```python:setting.py
ALLOWED_HOSTS = ['localhost']

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.postgresql',
        'NAME': 'postgres',
        'USER': 'postgres',
        'PASSWORD': 'postgres',
        'HOST': 'db',
        'PORT': 5432,
    }
}
```

**6.イメージの構築、コンテナの構築・起動**
以下のコマンドで、イメージの構築、コンテナの構築・起動します。

```
$ docker-compose up --build
```

**7.環境構築完了！**
http://localhost:8000/
にアクセスし、以下の画面が表示されればOKです！
![Screenshot from 2020-03-16 17-36-49.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/370196/b7576b1e-4726-ae21-1681-354f884cec74.png)

#データベースのセットアップ

```
$ docker-compose run web python3 manage.py migrate
```
このコマンドを実行すると、以下のようにマイグレーションが行われる。

![Screenshot from 2020-04-16 23-17-22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/370196/f0d72735-7019-540d-8898-f0a16a531935.png)


#新しいアプリケーションを作成する
アプリケーションを作成するために以下のコマンドを実行します。

```
$ docker-compose run web python3 manage.py  startapp todo
```

実行後のディレクトリ構成は以下の通りです。

```
django_todo
├── Dockerfile
├── django_todo
│   ├── __init__.py
│   ├── __pycache__
│   │   ├── __init__.cpython-38.pyc
│   │   ├── settings.cpython-38.pyc
│   │   ├── urls.cpython-38.pyc
│   │   └── wsgi.cpython-38.pyc
│   ├── settings.py
│   ├── urls.py
│   └── wsgi.py
├── docker-compose.yml
├── manage.py
├── requirements.txt
└── todo
    ├── __init__.py
    ├── admin.py
    ├── apps.py
    ├── migrations
    │   └── __init__.py
    ├── models.py
    ├── tests.py
    └── views.py
```

アプリケーションを作ったら、Djangoにそれを使うように伝える必要があります。 そのために、`django_todo/settings.py` のINSTALLED_APPS に`todo`を追加します。つまり`settings.py`は以下のようになります。

```python:setting.py
INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'todo',
]
```

また、ここでタイムゾーン、言語、静的ファイルのパスも以下のように設定しておきます。

```python:setting.py
LANGUAGE_CODE = 'ja'

TIME_ZONE = 'Asia/Tokyo'
```

```python:setting.py
STATIC_URL = '/static/'

STATIC_ROOT = os.path.join(BASE_DIR, 'static')
```

#おわりに
以上で環境構築は終了です！
ここまでのコードは[リポジトリのchapter1ブランチ](https://github.com/takusugar0/django_todo/tree/chapter1)にあります。
次のチャプターでは、フォルダ一覧表示を実装していきます！
[DjangoでTodoアプリを作る②フォルダ一覧ページの作成](https://qiita.com/takos/items/3e480183e72f41b69b84)

##記事一覧
[DjangoでTodoアプリを作る①Dockerで環境を構築する](https://qiita.com/takos/items/b9ba0b60c6f71b428aac)
[DjangoでTodoアプリを作る②フォルダ一覧ページの作成](https://qiita.com/takos/items/3e480183e72f41b69b84)
[DjangoでTodoアプリを作る③タスク一覧ページの作成](https://qiita.com/takos/items/828283aad5e5e2d8573d)
[DjangoでTodoアプリを作る④フォルダー、タスク作成機能の実装](https://qiita.com/takos/items/ce580c5781956a7c7eba)
[DjangoでTodoアプリを作る⑤タスク編集機能の作成](https://qiita.com/takos/items/dc4b91784cf895cc71c3)