前書き
この記事はPythonをバックエンド(Djangoをフレームワークとして使用)、Node.jsでWebpackを用いてVue.jsをフロントエンドとして使用できるようにするための備忘録記事です。
node.jsの知識が浅いので、使い方を間違っていることもあります。ご了承ください。
また、この記事はpipenv
やyarn
を使用しています。導入していない場合は導入してからこの記事を読むことをお勧めします。
パッケージのインストール
Djangoのstartprojectで自動作成されたフォルダを基にします。
Python
pip install django
django-admin startproject django_vuejs
cd django_vuejs
pipenv --python 3
pipenv install django
pipenv install django-webpack-loader==0.7.0
node.js
yarn init -yp # package.jsonを作る(対話なし)
yarn add --dev @babel/core @babel/preset-env
yarn add --dev babel-loader css-loader sass-loader style-loader vue-loader vue-template-compiler
yarn add --dev webpack webpack-cli
yarn add --dev webpack-bundle-tracker@0.4.3
yarn add vue vuex vue-router
yarn add --dev clean-webpack-plugin # これは任意ですが、これを入れておくとビルドしたjsファイルがかさばらなくなるので導入推奨。
気をつけてほしいのはwebpack-bundle-tracker
のバージョン指定です。バージョンが新しすぎてPython側のdjango-webpack-loader
が上手く動作しなかったため、バージョン指定しています1。念の為Python側のdjango-webpack-loader
のバージョンも指定してます。
設定
webpack
var path = require("path");
var webpack = require('webpack');
var BundleTracker = require('webpack-bundle-tracker');
var VueLoaderPlugin = require('vue-loader/lib/plugin');
var { CleanWebpackPlugin } = require('clean-webpack-plugin'); // clean-webpack-pluginを導入した場合は追記
module.exports = {
context: __dirname,
mode: process.env.NODE_ENV,
entry: {
main: './src-front/main.js'
},
output: {
filename: "[name]-[hash].js",
path: path.resolve('./static/build/')
},
plugins: [
new BundleTracker({
path: '.',
filename: 'webpack-stats.json'
}),
// clean-webpack-pluginを導入した場合は追記(ここから)
new CleanWebpackPlugin({
verbose: true
}),
// (ここまで)
new VueLoaderPlugin()
],
module: {
rules: [
{
test: /\.js$/,
loader: 'babel-loader'
},
{
test: /\.vue$/,
loader: 'vue-loader'
},
{
test: /\.scss$/,
use: [
'style-loader',
'css-loader',
'sass-loader'
]
},
{
test: /\.css$/,
use: [
'vue-style-loader',
'style-loader',
{
loader: 'css-loader',
options: {
url: false,
sourceMap: true
}
}
]
}
]
},
resolve: {
extensions: ['.js', '.vue'],
modules: [
'node_modules'
],
alias: {
'vue': path.resolve('./node_modules/vue/dist/vue.js')
}
}
}
Django
# (省略)
INSTALLED_APPS = [
# ...
# 以下の文を追記
'webpack_loader',
]
# 追記
WEBPACK_LOADER = {
'DEFAULT': {
'CACHE': not DEBUG,
'BUNDLE_DIR_NAME': 'build/',
'TIMEOUT': None,
'STATS_FILE': os.path.join(BASE_DIR, 'webpack-stats.json'),
'IGNORE': [r'.+\.hot-update.js', r'.+\.map']
}
}
STATICFILES_DIRS = [
os.path.join(BASE_DIR, 'static')
]
package.json
package.json
内に以下の内容を追記します。
--progress
オプションはwebpackの進捗状況を可視化できるオプションのため、不要であれば付ける必要はありません。
"scripts": {
"dev": "webpack --mode development --progress",
"build": "webpack --mode production --progress",
"watch": "webpack --watch -d --progress"
},
メインページ
これがフロントエンドがベースとなるファイルです。ここにwebpackでビルドしたCSSやjavascriptのリンクが埋め込まれます。
{% load render_bundle from webpack_loader %}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>django_vuejs</title>
{% render_bundle 'main' 'css' %}
</head>
<body>
<noscript>
<p>Your browser is disabled JavaScript. To use this web application, please enable JavaScript.</p>
</noscript>
<div id="app"></div>
{% render_bundle 'main' 'js' %}
</body>
</head>
Django URL
※今回は1ファイルにまとめていますが、適宜場所を移してください。
from django.contrib import admin
from django.urls import path
from django.shortcuts import render
def index(request):
return render(request, "index.html")
urlpatterns = [
path('admin/', admin.site.urls),
path('', index, name="index"),
]
フロントエンド
import Vue from 'vue'
import App from './App'
import router from './router.js'
import store from './store'
Vue.config.productionTip = false
const app = new Vue({
el: '#app',
router,
store,
template: "<App/>",
components: { App }
})
<template>
<div>
<p>Hello World!</p>
<router-view></router-view>
</div>
</template>
<script>
export default {
name: 'App'
}
</script>
<style>
</style>
./router.js
や./store
はVue.jsのコマンドで自動生成されるものともろ一緒なので、申し訳ないのですが割愛します。
gitignore (gitで管理する場合は設定)
# 追記
/static/build/
/webpack-stats.json
ビルド
本番用でビルドする場合はyarn run build
、
開発用としてビルドする場合はyarn run dev
またはyarn run watch
(フロントエンド系のソースを集中的に弄る場合は推奨)
のコマンドを実行します。
ビルドが完了したらpython manage.py runserver
でDjangoの開発サーバーを起動し、http://localhost:8000/
にアクセスすると、表示されるはずです。