webpack4 создает простое SPA-приложение

Webpack

открытие

Webpack — это инструмент, который нельзя обойти стороной в современной фронтенд-разработке. Особенно при разработке приложений SPA, будь то среда разработки или упаковка и запуск, это очень зависит от веб-пакета.

среда разработки

win10

node -v: 10.15.0

npm -v: 6.4.1

Поехали.

опыт 0 конфигурация

Перейдите в рабочий каталог и создайте проект

mkdir spa-webpack-demo

инициализация

npm init -y

Давайте сначала попробуемwebpack4из0配置:

Установить веб-пакет

npm i -D webpack

После установки зависимостей веб-пакета создайте папку src и создайте новую в srcindex.js.

mkdir src
cd src
type nul > index.js

Исправлятьpackage.json,существуетscriptsoptions, добавьте две команды:

"dev": "webpack --mode=development",
"prod": "webpack --mode=production"

Хорошо, мы закончили. Далее запускаем командную строку и тестируем

npm run dev

При нормальных обстоятельствах консоль будет иметь следующую подсказку, потому чтоwebpackкоманда требует зависимостейwebpack-cli, мы можем установить

Do you want to install 'webpack-cli' (yes/no): yes

webpack-cliПосле завершения установки он автоматически продолжит работу нашегоnpm run devкоманды, вы можете увидеть, что в проекте есть еще одна директория dist и еще однаmain.js.

Продолжить попытку дальшеnpm run prod, можно увидетьdist/main.jsбыл сжат.

ЭтоwebpackТак называемая нулевая конфигурация, основная работа заключается в определении значения по умолчанию.entryдорожкаsrc/index.js, который определяет значение по умолчаниюoutputдорожкаdist/main.js, а затем добавилmodeпараметры, согласноmodeРазница в параметрах помогает нам добавить несколько предустановленных правил упаковки.

шаг за шагом

В вышеописанном процессе я просто испытал ощущение нулевой конфигурации, и у меня даже нет html-файла, поэтому я начал добавлять его сюда.

Добавьте index.html

Новое в корневом каталогеindex.html, просто напишите что-нибудь

type nul > index.html

Говоря об обращенииhtmlфайл, однозначноhtml-webpack-plugin, установить его

npm i -D html-webpack-plugin

после этого项目根目录создать новыйwebpack.config.js, webpack будет использовать его автоматически

type nul > webpack.config.js

webpack.config.jsСодержание выглядит следующим образом

const HtmlWebpackPlugin = require('html-webpack-plugin');

module.exports = {
    module: {
        rules: []
    },
    plugins: [
        new HtmlWebpackPlugin({
            filename: 'index.html',
            template: 'index.html'
        })
    ]
}

воплощать в жизньnpm run dev, ты можешь видетьdistбольше папокindex.html,этоindex.htmlавтоматически вводил упакованныйdist/main.js.

добавить локальный сервер

index.htmlОн генерируется, но вы не можете открывать его вручную каждый раз, чтобы просмотреть его в браузере.Официальный веб-пакет рекомендует использоватьwebpack-dev-serverсделать сервер, установить его

npm i -D webpack-dev-server

После успешной установки изменитеwebpack.config.js,Добавить кdevServerварианты иwebpack.HotModuleReplacementPluginплагин.

Для содержимого, которое было добавлено в файл, я буду использовать комментарии позже.

const path = require('path');
const webpack = require('webpack');

function resolve(dir) {
    return path.join(__dirname, './', dir)
}

module.exports = {
    // module - 略
    devServer: {
        contentBase: resolve('dist'), // 根目录
        hot: true,   // 是否开启热替换,无须手动刷新浏览器
        port: 8081,    // 端口
        open: true,     // 是否自动打开浏览器
        noInfo: true   // 不提示打包信息,错误和警告仍然会显示
    },
    plugins: [
        new webpack.HotModuleReplacementPlugin(),
        // HtmlWebpackPlugin - 略
    ]
}

затем изменитьpackage.json scriptsизdevОпции

"dev": "webpack-dev-server --mode=development",

Примечание: когдаdevServerизhotПараметрыtrueКогда, не забудьте добавить в плагинnew webpack.HotModuleReplacementPlugin(), или вы можете ввести его в командной строке с помощьюhotпараметры, поэтому вам не нужно переходить кpluginsДобавлен плагин.

"dev": "webpack-dev-server --hot --mode=development"

потомnpm run dev, можешь попробовать静态资源Функция горячей замены теперь.

Обработка js, css и других статических ресурсов

Прежде всего, нам нужно уяснить, что сам вебпак не умеет обращаться со статическими ресурсами, но предоставляетloaderа такжеpluginмеханизм.

loaderРоль, как следует из названия: загрузчик, то есть подобранные статические ресурсы, должен пройти черезloaderвнутреннюю обработку, а затем вернуть результат после обработки. Я думаю,loaderкак перехватчик.

Когда дело доходит до js, мы будем думать оbabel-loader,babel-loaderДля чего это? Нормальная работа должна соответствоватьjs文件Код ES6 согласноbabelrc文件内的配置Скомпилируйте в соответствующий код ES5.

Давайте добавим.babelrcдокумент

новый.babelrcдокумент

type nul > .babelrc

редактировать.babelrcсодержание

{
    // 预设置,告诉Babel要转换的源码使用了哪些新的语法特性
    // targets, useBuiltIns 等选项用于编译出兼容目标环境的代码
    // 其中 useBuiltIns 如果设为 "usage"
    // Babel 会根据实际代码中使用的 ES6/ES7 代码,以及与你指定的 targets,按需引入对应的 polyfill
    // 而无需在代码中直接引入 import '@babel/polyfill',避免输出的包过大,同时又可以放心使用各种新语法特性。
    "presets": [
        ["@babel/preset-env", {
            // modules 是否 将 ES6 的 import/export模块化 转为 babel 的 CommonJs 规范模块化
            "modules": false,
            "targets": {
                // "> 1%" : 支持市场份额超过1%的浏览器, 
                // ""last 2 versions"": 支持每个浏览器最后两个版本
                // "not ie <= 8": 在之前条件的浏览器中,排除 IE8 以下的浏览器
                "browsers": ["> 1%", "last 2 versions", "not ie <= 8"]
            },
            "useBuiltIns": "usage"
        }]
    ],
    // 所用插件
    // transform-runtime 插件表示不管浏览器是否支持ES6,只要是ES6的语法,它都会进行转码成ES5
    // 这个是需要优化的
    "plugins": ["@babel/plugin-transform-runtime"]
}

УстановитьbabelЗависимость, примечание:

babel 7+ 已经废弃了presets 中 stage-x 的用法,改为在plugins中添加。并且应用了npm scope包,代码全部在 @babel 中,避免以前那种 babel-preset-xxx, babel-plugin-xxx 的用法

最新的 babel-loader 版本是8+,需要依赖 babel-core 版本7+,包名为 @babel/core, 版本6+的包名为 babel-core.

再分析上面的 .babelrc 文件,它用到了@babel/preset-env, @babel/plugin-transform-runtime, 这些依赖都要我们安装好

如果使用了 @babel/preset-env,则不支持在 plugins 中 添加 stage-x

npm i -D babel-loader @babel/core @babel/preset-env @babel/plugin-transform-runtime

Когда дело доходит до css, мы должны думать оstyle-loaderа такжеcss-loader. сначала установите их

npm i -D style-loader css-loader

переустановитьurl-loaderИспользуется для анализа статических ресурсов, таких как изображения, шрифты и т. д.

npm i -D url-loader

затем изменитьwebpack.config.jsизrules, добавьте следующий код

module.exports = {
    module: {
        rules: [
            {
                test: /\.js$/,
                loader: 'babel-loader', 
                include: [
                    resolve('src'),
                    resolve('node_modules/webpack-dev-server/client')
                ]
            },
            {
                test: /\.css$/,
                use: ['style-loader', 'css-loader']
            },
            {
                test: /\.(png|jpe?g|gif|svg)(\?.*)?$/,
                loader: 'url-loader',
                exclude: [],
                options: {
                    limit: 10000,
                    name: 'img/[name].[hash:7].[ext]'
                }
            }
        ]
    },
    // devServer - 略
    // plugins - 略
}
Далее я готов к разработке, давайте использовать vue.

Vue не нужно устанавливать в devDependencies.

npm i -S vue 
// vue-loader 依赖 vue-template-compiler 和 vue-style-loader
npm i -D vue-loader vue-template-compiler vue-style-loader

Исправлятьwebpack.config.js, добавьте следующий код

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

module.exports = {
    resolve: {
        extensions: ['.js', '.vue', '.json'],
        alias: {
            '@': resolve('src')
        }
    },
    module: {
        rules: [
            {
                test: /\.vue$/,
                loader: 'vue-loader'
            },
            
            // 其他 - 略
        ]
    },
    // devServer - 略
    plugins: [
        // 加在最前面
        new VueLoaderPlugin()
        
        // 其他 - 略
    ]
}

Создайте новый каталог представлений и каталог активов в src,

Я добавил файл logo.png в каталог активов

Создайте компонент myTest в представлениях,myTest/index.vue, отредактируйте index.vue

<template>
    <div>
        <i class="logo"></i>
    </div>
</template>

<script>
export default {
    name: 'myTest'
}
</script>

<style scoped>
    .logo {
        display: block;
        margin: auto;
        width: 400px;
        height: 400px;
        background: url(../../assets/logo.png);
    }
</style>

srcСоздайте новый в каталогеApp.vue, содержание следующее

<template>
  <div id="app">
    <my-test></my-test>
  </div>
</template>

<script>
import myTest from "./views/myTest/index";

export default {
  name: "App",
  components: {
    myTest
  }
};
</script>

редактироватьsrcв каталогеindex.js, содержание следующее:

import Vue from 'vue';

import App from './App';

new Vue({
    el: '#app',
    render: h => h(App)
})

наконецnpm run devчтобы увидеть эффект.

глазурь на торте

Добавьте информацию индикатора выполнения упаковки, как показано ниже.
npm i -D progress-bar-webpack-plugin

Исправлятьwebpack.config.js

const ProgressBarPlugin = require('progress-bar-webpack-plugin');

// ....

plugins: [
    // 其他 - 略
    new ProgressBarPlugin()
]
Добавить уведомление о результатах упаковки
npm i -D webpack-build-notifier

Исправлятьwebpack.config.js

const WebpackBuildNotifierPlugin = require('webpack-build-notifier');

// ....

plugins: [
    // 其他 - 略
    new WebpackBuildNotifierPlugin()
]
Упаковка секретной информации
npm i -D webpack-dashboard

Исправлятьwebpack.config.js

const DashboardPlugin = require('webpack-dashboard/plugin');

// ....

plugins: [
    // 其他 - 略
    new DashboardPlugin()
]

Исправлятьpackage.json

"dev": "webpack-dashboard -- webpack-dev-server --mode=development"

Я использовал это, но эффект не очень идеален. Он откроет новое окно, и я не могу прокрутить, чтобы просмотреть информацию. Я не знаю, использовал ли я его неправильно.

Эффект показан на рисунке:

Вся структура кода показана на рисунке:

незавершенная функция

  1. productionсреда, необходимо использоватьmini-css-extract-pluginа такжеoptimize-css-assets-webpack-pluginПлагины, извлечение и оптимизация файлов css
  2. productionсреда, необходимо использоватьUglifyJsPluginПлагин, сжимающий файлы js, этот плагин позволяет многоядерную компиляцию
  3. productionсреда, необходимо использоватьoptimizationОпцииsplitChunks
  4. vue-routerа такжеvuexвступление к
  5. так далее

напиши в конце

Я надеюсь, что процесс этой статьи может помочь нуждающимся читателям.Кроме того, функция упаковки в этой статье относительно грубая, а скорость упаковки относительно низкая.Если у вас есть какие-либо предложения, сообщите мне об этом в комментариях.

Если есть ошибки, пожалуйста, укажите на них. Спасибо за прочтение.

кодовый адресspa-webpack-demo

Ссылаться на

официальная документация бабеля

Подробное руководство по многоканальной конфигурации Webpack4 + babel7