序
python+conda以外の全ての知識がなかったのでかなり苦労してdjango+docker+heroku環境を整えた。
今回は化合物のSMILESを入力として受け取り、その化合物を表示するところまで行きます。
参考にしたサイト様
Docker上でAnacondaを使って入れたDjangoをHerokuで動かす
HerokuにConda環境で開発したアプリをデプロイする方法
Django 入門
環境
Window 11
anaconda
VScode
1. Dockerでコンテナを作成する。
Docker上でAnacondaを使って入れたDjangoをHerokuで動かすの2,3,4,5を参照してください。condaの仮想環境に入った後にインストールするものはanacondaからdjango環境を作ると同じものを入れてください。
最後にdocker commit django djangotest:1.0.0
などで適当にdockerを保存しておきます。
2. anacondaからdjango環境を作る。
名前は何でもよいのでwindows 11環境でdjango環境を作ります。(anaconda環境の作成は省略)
rdkitはお好みでインストールしてください。普通のアプリ作るならいらないです。
(base) > conda create -n django_env python==3.7
(base) > conda activate django_env
(django_env) > conda install django=3.* -c conda-forge
(django_env) > conda install -c rdkit -c conda-forge rdkit
(django_env) > conda install django-heroku -c conda-forge
次にdjangoでアプリケーションを作ります。
プロジェクト名:wepapps、アプリ名:chem_appで作ります。
(django_env) > mkdir django_sample
(django_env) > cd django_sample
(django_env) > mkdir webapps
(django_env) > cd webapps
(django_env) > django-admin startproject webapps .
(django_env) > python manage.py startapp chem_app
django-admin startproject webapps .
は、mkdir webapps
と同じ名前である必要はないです。
ここで一旦python manage.py runserver 0.0.0.0:8000
として動くかどうかを確認します。
3. アプリケーションを作る
django_sample/webapps/webapps/setting.py
で、以下を変更。
# herokuでアクセスできるようにしておく
ALLOWED_HOSTS = ['127.0.0.1', '.herokuapp.com']
~
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [
# htmlを読み込めるようにしておく。
os.path.join(BASE_DIR, 'chem_app/templates'), ## <- ココを追加
],
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]
次にdjango_sample/webapps/webapps/urls.py
を以下のように変更する。
from django.conf.urls import url, include
from django.contrib import admin
from django.urls import path
import chem_app.views as chem # django_sample/webapps/chem_app/views.pyをchemとして扱っています
urlpatterns = [
path('admin/', admin.site.urls),
path('smiles2picture/', chem.smiles2pic, name='smiles2picuture'),
path('smiles2picture/result', chem.smiles2pic_result, name='s2p_res'),
]
django_sample/webapps/chem_app/views.py
を以下のように変更する。
from django.shortcuts import render
from django.http import HttpResponse # Load Module
from rdkit import Chem
from rdkit.Chem import Draw
import base64
from io import BytesIO
from PIL import Image
import os
def pil_to_base64(img, format="jpeg"):
buffer = BytesIO()
img.save(buffer, format)
img_str = base64.b64encode(buffer.getvalue()).decode("ascii")
return img_str
def smiles2pic(request):
return render(request,"smiles2picture.html")
def smiles2pic_result(request):
# SMILESから画像を生成する
smiles = request.POST.get("SMILES", None)
print(f"smiles:{smiles}")
m = Chem.MolFromSmiles(smiles)
img = Draw.MolToImage(m,size=(300, 300))
img_base64 = pil_to_base64(img, format="png")
return render(request, 'chemtest.html',{"title":smiles,"img":img_base64})
django_sample/webapps/chem_app/templates/smiles2picture.html
及びをdjango_sample/webapps/chem_app/templates/chemtest.html
以下のようにして追加する。
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>Smiles2Picture</title>
</head>
<body>
<p>化合物のSMILESを入力</p>
<form action="/smiles2picture/result" method="POST">
{% csrf_token %}
<input type="text" name="SMILES">
<input type="submit" value="送信">
</form>
</body>
</html>
<!doctype html>
<html lang="ja">
<head>
<meta charset="utf-8">
<title>{{ title }}</title>
</head>
<body>
<img src="data:image/png;base64,{{img}}">
</body>
</html>
ここではrdkitで生成した画像をファイルに保存せずにbase64にして直接htmlファイルに渡していますが、これはherokuがファイルの保存して使いまわすようなことができないからです。staticな場合にはdjangoの方でちょっと面倒な操作が必要みたいです。
ここでもう一度python manage.py runserver 0.0.0.0:8000
を打って http://127.0.0.1:8000/smiles2picture/ にアクセスしてきちんと動くか確認します。
4.Dcokerfileを生成する。
django_sample
直下にはDockerfile
を設置します。
# 自分のdockerイメージに書き換える
FROM djangotest:1.0.2
SHELL ["/bin/bash", "-c","-l"]
RUN echo "chmod 777 /root/.pyenv/versions/miniconda3-latest/etc/profile.d/conda.sh" >> ~/.bashrc
RUN echo "source /root/.pyenv/versions/miniconda3-latest/etc/profile.d/conda.sh" >> ~/.bashrc
RUN echo "conda activate base" >> ~/.bashrc
RUN echo "conda activate django" >> ~/.bashrc
RUN echo "conda env list" >> ~/.bashrc
ENV PATH /root/.pyenv/versions/miniconda3-latest/envs/django/bin:$PATH
COPY webapps/ ~/webapps
WORKDIR ~/webapps
CMD gunicorn --bind 0.0.0.0:$PORT webapps.wsgi
5. herokuの導入。
gitが入っている必要があり。
公式サイトから自環境にあったものを選択して導入。
それからheroku CLIを入れる。windowsだと割と何も考えずにできる。
6. herokuでpushする。
heroku container:login
heroku create myappname
heroku container:push web -a myappname
heroku container:release web -a myappname
これでherokuに適用されたはずです。自分の作ったサイトにアクセスして動くか確かめてみましょう。
だめならheroku logs --tail -a myappname
でログが確認できます。
私の作ったサイトを仮公開しておきます。https://mychemodel2.herokuapp.com/smiles2picture
補遺・最終的なディレクトリ構造
DJANGO_SAMPLE
│ Dockerfile
│
└─webapps
│ db.sqlite3
│ manage.py
│
├─chem_app
│ │ admin.py
│ │ apps.py
│ │ models.py
│ │ tests.py
│ │ views.py
│ │ __init__.py
│ │
│ ├─migrations
│ │ __init__.py
│ │
│ ├─static
│ │ └─chem_app
│ │ └─images
│ │ └─ test.png
│ │
│ └─templates
│ chemtest.html
│ index.html
│ smiles2picture.html
│
└─webapps
│ asgi.py
│ settings.py
│ urls.py
│ wsgi.py
└─ __init__.py