DjangoにPlotlyのグラフを表示する
背景
データを扱ったWebアプリケーションでは、そのデータを可視化してダッシュボードのように表示したい場合があると思います。 Dash を利用することでインタラクティブにデータを可視化できるWebアプリケーションを容易に構築できます。
Dashは予めデータが用意されている場合には便利なフレームワークですが、ユーザがデータを入力するケースなどにおいてはDjangoのようなモデルが用意されているフレームワークを検討してもよいかもしれません。
ようやく本題となりますが、DjangoのWebアプリケーションのデータの可視化部分を plotly.py で実装してみます。
plotly.pyを利用する利点としては次のようなものが挙げられます。
- インタラクティブな可視化が実装できる
- さまざまな分野に対応した多数のグラフライブラリが用意されている
- HTML形式に出力できるため、テンプレートにすばやく組み込める
実装手順
今回は可視化部分の実装方法を理解しやすくするため、必要最低限の構成にします。
Python3.6以降の仮想環境を用意し、必要なライブラリをインストールします。
pip install plotly django
プロジェクトとアプリケーションを作成します。
django-admin startproject mysite
cd mysite
python manage.py startapp app
次のようなディレクトリ構成になります。
tree
.
├── app
│ ├── __init__.py
│ ├── admin.py
│ ├── apps.py
│ ├── migrations
│ │ └── __init__.py
│ ├── models.py
│ ├── tests.py
│ └── views.py
├── manage.py
└── mysite
├── __init__.py
├── __pycache__
│ ├── __init__.cpython-38.pyc
│ └── settings.cpython-38.pyc
├── asgi.py
├── settings.py
├── urls.py
└── wsgi.py
mysite/settings.py
に作成したアプリケーションとテンプレートのディレクトリを登録します(#追記の行)。
# Application definition
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'app', # 追記
]
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [BASE_DIR / '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',
],
},
},
]
URLディスパッチャを追加します。今回はルート(/
)にグラフが描画されるだけのWebアプリケーションにします。
from django.contrib import admin
from django.urls import path, include
from django.views.generic.base import RedirectView
urlpatterns = [
path('admin/', admin.site.urls),
path('', include(('app.urls', 'app'), namespace='app', )),
]
from django.urls import path
from . import views
urlpatterns = [path("", views.LineChartsView.as_view(), name="plot")]
ビューを作成します。ここが今回のポイントです。plotly.pyで描画したデータをHTMLに出力してテンプレートに渡します。今回は TemplateView
を利用します(❶)。
plotly.pyには figure と呼ばれる描画領域を管理するオブジェクトがあり、このオブジェクトからHTML上にグラフを描画したり、Jupyter上にグラフを描画できます。今回は紹介していませんが、 Plotly Express についても同様です。
figure オブジェクトをHTMLに出力するには to_html
メソッドを実行します(❷)。plotly.pyは plotly.js が元になったラッパーで、HTMLにはJavaScriptが含まれますが、後述するCDNを利用するため、引数 include_plotlyjs
を False
にしてJavaScript部分以外を出力します。
plotly.pyのグラフがHTML化できたので、これを TemplateView
に追加します(❸)。
from django.views.generic import TemplateView # ❶
import plotly.graph_objects as go
def line_charts():
fig = go.Figure(
go.Scatter(x=[1, 2, 3], y=[3, 5, 2]), layout=go.Layout(width=400, height=400)
)
return fig.to_html(include_plotlyjs=False) # ❷
class LineChartsView(TemplateView): # ❶
template_name = "plot.html"
def get_context_data(self, **kwargs):
context = super(LineChartsView, self).get_context_data(**kwargs)
context["plot"] = line_charts() # ❸
return context
上記で出力したHTMLをテンプレートに組込みます。ヘッダにはplotly.jsのCDNを参照し、上記のビューで生成したHTMLを渡します。
{% block head %}
<script src="https://cdn.plot.ly/plotly-latest.min.js"></script>
{% endblock %}
{% block content %}
<div class="title"><h1>Plotlyのグラフを描画</h1></div>
<div class="graph">{{plot|safe}}</div>
{% endblock %}
マイグレーション
一通りのファイルが準備できたらマイグレーションして終了です。
python manage.py makemigrations
python manage.py migrate
動作確認
Webサーバを起動すると、ブラウザ上には下記のように表示されます。
python manage.py runserver
サンプルプロジェクト
本記事のソースコードを次のリポジトリに用意しました。
Discussion