15
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

スクラッチからWebpack+Babel+Vue 3を使う

Last updated at Posted at 2020-10-24

スクラッチからWebpack+Babel+Vue.jsを使う をVue 3に対応させてみました。

Vue CLI も Rails+Webpacker も使わずに、Vue.js(Single File Component)のバージョン3を試す方法です。スクラッチから作るのが好きな人、WebpackとBabelが吐いたコードを眺めたい人はどうぞ。

準備

てきとうなディレクトリを作り、yarnで必要なモジュールをインストールします。

% mkdir scratch && cd scratch
% yarn add @babel/core @babel/preset-env babel-loader core-js vue@next vue-loader@next @vue/compiler-sfc vue-template-compiler webpack webpack-cli

vue と vue-loader をVue 3のものにするために vue@nextvue-loader@next とします。また、vue-loader を動かすのに @vue/compiler-sfc が必要です。

最終的なディレクトリとファイルの配置は次のようになります。

- dist
  - app.js
  - app.js.map
- node_modules
- src
  - app.js
  - hello.vue
- babel.config.js
- index.html
- package.json
- wbpack.config.js
- yarn.lock

Vueアプリケーション

HTMLと簡単なVueアプリケーションを書きます。Vue 2との違いは、アプリケーションを作成してマウントする部分 createApp(Hello).mount('#app'); だけです。

index.html
<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>てすと</title>
    <script src="dist/app.js"></script>
  </head>
  <body>
    <div id="app"></div>
  </body>
</html>
src/app.js
import "core-js/stable";
import "regenerator-runtime/runtime";

import { createApp } from 'vue';
import Hello from './hello.vue';

document.addEventListener('DOMContentLoaded', () => {
  createApp(Hello).mount('#app');
});
src/hello.vue
<template>
  <div>
    <h1>{{message}}</h1>
    <p><input v-model="message"></p>
  </div>
</template>

<script>
export default {
  data() {
    return {
      message: ''
    };
  },
  created() {
    this.message = 'hello';
  }
}
</script>

webpack.config.js

webpack.config.js を書きます。src/app.js が dist/app.js に出力されるようにします。

webpack.config.js
const { VueLoaderPlugin } = require('vue-loader');
const webpack = require('webpack');
const path = require('path');

const env = process.env.NODE_ENV || 'development';

module.exports = {
  entry: './src/app.js',
  output: {
    filename: 'app.js',
    path: path.resolve(__dirname, 'dist'),
  },
  devtool: 'source-map',
  mode: env,
  module: {
    rules: [
      {
        test: /\.vue$/,
        loader: 'vue-loader'
      },
      {
        test: /\.js$/,
        loader: 'babel-loader'
      }
    ]
  },
  plugins: [
    new VueLoaderPlugin(),
    new webpack.DefinePlugin({
      __VUE_OPTIONS_API__: true,
      __VUE_PROD_DEVTOOLS__: false
    })
  ]
}

1行目は、Vue 2では、

const VueLoaderPlugin = require('vue-loader/lib/plugin');

としていたところをVue 3ではちょっと変えます。

const { VueLoaderPlugin } = require('vue-loader');

plugins: のところで、2つのオプションを指定していますが、これがないと実行時にWarningが出ます(Bundler Build Feature Flags を参照)。

    new webpack.DefinePlugin({
      __VUE_OPTIONS_API__: true,
      __VUE_PROD_DEVTOOLS__: false
    })

babel.config.js

IE 11対応にするために、babel.config.js に preset-env の設定を書きます。ここは Vue 2のものから変えていません。

babel.config.js
module.exports = api => {
  api.cache(true);

  return {
    presets: [
      [
        "@babel/preset-env",
        {
          targets: { ie: "11" },
          useBuiltIns: "entry",
          corejs: 3
        }
      ]
    ]
  }
}

コンパイル

package.json に scripts.build を追加すると、yarnコマンドでwebpackを呼び出せます。

package.json
{
  "scripts": {
    "build": "webpack --config=webpack.config.js"
  },
  "dependencies": {
    "@babel/core": "^7.12.3",
    "@babel/preset-env": "^7.12.1",
    "@vue/compiler-sfc": "^3.0.2",
    "babel-loader": "^8.1.0",
    "core-js": "^3.6.5",
    "vue": "^3.0.2",
    "vue-loader": "^16.0.0-beta.8",
    "vue-template-compiler": "^2.6.12",
    "webpack": "^5.2.0",
    "webpack-cli": "^4.1.0"
  }
}

yarn build とすると、webpackが dist/app.js を生成します。

% yarn build

環境変数 NODE_ENV を production にすると、本番環境用に圧縮された dist/app.js ができます。

% NODE_ENV=production yarn build

index.html を ブラウザーで開いてVueアプリケーションが動けば成功です。

2020-12-15 追記: app.js に以下の2行を入れても、Vue 3はIE 11で動きません。「catch ステートメントでは適用されますが、throw ステートメントでは適用されません。」のエラーが出ます(throw TypeError が引っかかる)。core-jsで発生するエラーのようです( https://github.com/zloirock/core-js/issues/514 )。core-jsを最新版に上げてもダメでした。

src/app.js
import "core-js/stable";
import "regenerator-runtime/runtime";
15
10
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
15
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?