Подробно разблокируйте серию Webpack (дополнительно)

внешний интерфейс JavaScript
Подробно разблокируйте серию Webpack (дополнительно)

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

Это вторая, если вы еще не читали«Возьми у вас в нескольких минутах разблокировки серии WebPack (Basic)», рекомендуется продолжить чтение этой статьи после ее прочтения.

Эта статья расскажет большеwebpackКонфигурация, если есть какие-то ошибки в тексте, добро пожаловать, исправьте их в комментариях, я исправлю их как можно скорее.webpackЧасть оптимизации размещена в следующей статье.

Рекомендуется обратиться к этой статье для пошаговой настройки.Не всегда думайте о поиске лучшей конфигурации.Освоив ее, настройте ее в соответствии с вашими потребностями, которая является лучшей конфигурацией.

Адрес проекта, соответствующий этой статье (использованный при написании этой статьи), предназначен для справки:GitHub.com/Иветт Л.А. У/И…

1. Копия статического ресурса

Иногда нам нужно использовать существующие файлы JS, файлы CSS (локальные файлы), но нет необходимостиwebpackкомпилировать. Например, мыpublic/index.htmlвведен вpublicв каталогеjsилиcssдокумент.这个时候,如果直接打包,那么在构建出来之后,肯定是找不到对应的js / css.

publicСтруктура каталогов

├── public
│   ├── config.js
│   ├── index.html
│   ├── js
│   │   ├── base.js
│   │   └── other.js
│   └── login.html

Теперь мыindex.htmlвведен в./js/base.js.

<!-- index.html -->
<script src="./js/base.js"></script>

В это время мыnpm run dev, вы увидите сообщение об ошибке, что файл ресурсов не найден.

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

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

050a81c7-59e4-4596-b08f-62cefce353d0.jpg

К счастью,webpackПредоставляет полезный плагин для тех из нас, у кого плохая память и кто любит лениться.CopyWebpackPlugin, все, что он делает, это копирует один файл или весь каталог в каталог сборки.

Сначала установите зависимости:

npm install copy-webpack-plugin -D

Изменить конфигурацию (ток необходимо сделать, этоpublic/jsкопия каталога вdist/jsсодержание):

//webpack.config.js
const CopyWebpackPlugin = require('copy-webpack-plugin');
module.exports = {
    //...
    plugins: [
        new CopyWebpackPlugin([
            {
                from: 'public/js/*.js',
                to: path.resolve(__dirname, 'dist', 'js'),
                flatten: true,
            },
            //还可以继续配置其它要拷贝的文件
        ])
    ]
}

В этот момент повторите выполнениеnpm run dev, сообщение об ошибке исчезло.

Скажи это здесьflattenЭтот параметр установлен наtrueТогда он будет только скопировать файл, а не путь папки, вы не можете установитьflatten, посмотрите на результаты сборки.

Кроме того, если мы хотим скопировать много файлов в каталог, но хотим отфильтровать один или несколько файлов, тогдаCopyWebpackPluginтакже предоставляет намignoreпараметр.

//webpack.config.js
const CopyWebpackPlugin = require('copy-webpack-plugin');
module.exports = {
    //...
    plugins: [
        new CopyWebpackPlugin([
            {
                from: 'public/js/*.js',
                to: path.resolve(__dirname, 'dist', 'js'),
                flatten: true,
            }
        ], {
            ignore: ['other.js']
        })
    ]
}

Например, здесь мы игнорируемjsв каталогеother.jsфайл, использоватьnpm run buildПостроить, вы можете увидетьdist/jsне появитсяother.jsдокумент.CopyWebpackPluginТакже предусмотрено множество других параметров.Если текущая конфигурация вас не устраивает, вы можете обратиться к документации для дальнейшего изменения конфигурации.

2.ProvidePlugin

ProvidePluginНа мой взгляд, это для ленивых, но не злоупотребляйте, ведь глобальные переменные - это не "хорошо".ProvidePluginЭффект в том, что он не нуженimportилиrequireЕго можно использовать везде в проекте.

ProvidePluginдаwebpackВстроенный плагин используется следующим образом:

new webpack.ProvidePlugin({
  identifier1: 'module1',
  identifier2: ['module2', 'property2']
});

Путь поиска по умолчанию — текущая папка../**а такжеnode_modules, конечно, можно указать полный путь.

ReactКак мы все знаем, при использовании его следует вносить в каждый файлReact, а то сразу выкину ошибку на ваше обозрение. И естьjquery, lodashТакая библиотека может использоваться в нескольких файлах, но мне лень ее каждый раз вводить, ну что же, поленимся и доработаем.webpackКонфигурация:

const webpack = require('webpack');
module.exports = {
    //...
    plugins: [
        new webpack.ProvidePlugin({
            React: 'react',
            Component: ['react', 'Component'],
            Vue: ['vue/dist/vue.esm.js', 'default'],
            $: 'jquery',
            _map: ['lodash', 'map']
        })
    ]
}

После этой конфигурации вы можете использовать в проекте все, что захотите.$,_map, и написатьReactкомпоненты, ниimport Reactа такжеComponentТеперь, если вы хотите, вы также можете поставитьReactизHooksнастраиваются здесь.

Помимо,VueЕсть дополнительный после настройкиdefault,Это потому чтоvue.esm.jsиспользуется вexport defaultЭкспортируется, для этого необходимо указатьdefault.Reactиспользуетmodule.exportsэкспортируется, так что не пишитеdefault.

Кроме того, если ваш проект начинаетсяeslintЕсли это так, не забудьте изменитьeslintфайл конфигурации, добавьте следующую конфигурацию:

{
    "globals": {
        "React": true,
        "Vue": true,
        //....
    }
}

Конечно, должна быть определенная степень лени.Если вы настраиваете много глобальных переменных, вы можете в конечном итоге создать себе проблемы.Вы должны нести ответственность за глобальные переменные, которые вы настраиваете до конца.

u=2243033496,1576809017&fm=15&gp=0.jpg

3. Извлеките CSS

Мы уже говорили об упаковке CSS, но иногда у нас может возникнуть необходимость извлечения файлов CSS, то есть упаковки файлов CSS отдельно, это может быть связано с тем, что упаковка в файл JS слишком велика, что влияет на скорость загрузки, или это может быть За кеширование (например, изменилась только часть JS), или "я доволен": хочу оторваться и никому нет дела.

Независимо от того, каковы ваши причины для абстрагирования CSS, если вам это нужно, мы можем это сделать.

Сначала установитеloader:

npm install mini-css-extract-plugin -D

mini-css-extract-pluginа такжеextract-text-webpack-pluginв сравнении с:

  1. Асинхронная загрузка
  2. Без перекомпиляции (лучше производительность)
  3. проще в использовании
  4. только CSS

Модифицируем наш конфигурационный файл:

//webpack.config.js
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
module.exports = {
    plugins: [
        new MiniCssExtractPlugin({
            filename: 'css/[name].css'
            //个人习惯将css文件放在单独目录下
            //publicPath:'../'   //如果你的output的publicPath配置的是 './' 这种相对路径,那么如果将css文件放在单独目录下,记得在这里指定一下publicPath 
        })
    ],
    module: {
        rules: [
            {
                test: /\.(le|c)ss$/,
                use: [
                    MiniCssExtractPlugin.loader, //替换之前的 style-loader
                    'css-loader', {
                        loader: 'postcss-loader',
                        options: {
                            plugins: function () {
                                return [
                                    require('autoprefixer')({
                                        "overrideBrowserslist": [
                                            "defaults"
                                        ]
                                    })
                                ]
                            }
                        }
                    }, 'less-loader'
                ],
                exclude: /node_modules/
            }
        ]
    }
}

Теперь перекомпилируем:npm run build, структура каталогов выглядит следующим образом:

.
├── dist
│   ├── assets
│   │   ├── alita_e09b5c.jpg
│   │   └── thor_e09b5c.jpeg
│   ├── css
│   │   ├── index.css
│   │   └── index.css.map
│   ├── bundle.fb6d0c.js
│   ├── bundle.fb6d0c.js.map
│   └── index.html

Как я уже говорил, лучше создать новый.browserslistrcфайл, так что несколькоloaderОбщая конфигурация, поэтому вручную создайте новый файл в корневом каталоге (.browserslistrc), содержимое выглядит следующим образом (вы можете изменить его на другие конфигурации в соответствии с потребностями вашего проекта):

last 2 version
> 0.25%
not dead

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

//webpack.config.js
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
module.exports = {
    //...
    plugins: [
        new MiniCssExtractPlugin({
            filename: 'css/[name].css' 
        })
    ],
    module: {
        rules: [
            {
                test: /\.(c|le)ss$/,
                use: [
                    MiniCssExtractPlugin.loader,
                    'css-loader', {
                        loader: 'postcss-loader',
                        options: {
                            plugins: function () {
                                return [
                                    require('autoprefixer')()
                                ]
                            }
                        }
                    }, 'less-loader'
                ],
                exclude: /node_modules/
            },
        ]
    }
}

проверить свой собственный.browserlistrcЯвляется ли это эффективным или нет, также очень просто, напрямую измените содержимое файла, чтобыlast 1 Chrome versions, а потом сравните результаты построения до и после модификации, это видно.

Вы можете просмотреть дополнительные элементы конфигурации [browserslistrc] (GitHub.com/история браузеров…)

Дополнительные элементы конфигурации можно просмотретьmini-css-extract-plugin

Сжать извлеченный файл css

использоватьmini-css-extract-plugin,CSSФайл не будет сжат по умолчанию.Если вы хотите сжать, вам нужно настроитьoptimization, первая установкаoptimize-css-assets-webpack-plugin.

npm install optimize-css-assets-webpack-plugin -D

Измените конфигурацию веб-пакета:

//webpack.config.js
const OptimizeCssPlugin = require('optimize-css-assets-webpack-plugin');

module.exports = {
    entry: './src/index.js',
    //....
    plugins: [
        new OptimizeCssPlugin()
    ],
}

Обратите внимание, что здесьOptimizeCssPluginнапрямую настраивается вpluginsвнутрь, тоjsа такжеcssмогут быть сжаты нормально, если вы настроите это вoptimization, то вам нужно настроить его сноваjsСжатие (сжатие CSS не требуется в среде разработки, поэтому не забудьте указать его вwebpack.config.prod.jsКитай и Казахстан).

После завершения настройки в ходе тестирования обнаруживается, что после извлечения изменитьcssФайл, первая страница обновится, а вторая страница не обновится - ну не надо мне оттягиваться по своим обычным деламcss, этот вопрос отложили на сутки (точнее, забыли).

Когда я снова пересмотрел эту статью 8 марта, я просто увидел ееMiniCssExtractPlugin.loaderсоответствующийoptionнастройки, мы изменяем соответствующиеrule.

module.exports = {
    rules: [
        {
            test: /\.(c|le)ss$/,
            use: [
                {
                    loader: MiniCssExtractPlugin.loader,
                    options: {
                        hmr: isDev,
                        reloadAll: true,
                    }
                },
                //...
            ],
            exclude: /node_modules/
        }
    ]
}

4. загружается по запросу

Много раз нам не нужно загружать все файлы JS сразу, а нужно загружать требуемый код на разных этапах.webpackВстроенная мощная функция разделения кода позволяет реализовать загрузку по требованию.

Например, после того, как мы нажмем кнопку, нам нужно использовать код в соответствующем файле JS, нам нужно использоватьimport()грамматика:

document.getElementById('btn').onclick = function() {
    import('./handle').then(fn => fn.default());
}

import()грамматика, обязательно@babel/plugin-syntax-dynamic-importподдержка плагинов, но поскольку текущая@babel/preset-envПредустановка уже содержит@babel/plugin-syntax-dynamic-import, поэтому нам больше не нужно устанавливать и настраивать его отдельно.

непосредственныйnpm run buildBuild, результат сборки следующий:

WechatIMG1121.jpeg

webpackвстретитьimport(****)Когда используется этот синтаксис, он будет обрабатываться следующим образом:

  • Создайте новый с **** в качестве записиChunk
  • Когда код выполняется дляimportОператор, в котором он расположен, загрузитChunkСоответствующий файл (например, 1.bundle.8bf4dc.js здесь)

Вы можете сделать это в консоли вашего браузера по адресуNetworkизTab页Проверьте ситуацию с загрузкой файла, только после нажатия будет загружен соответствующий файлJS.

5. Горячее обновление

  1. настроить сначалаdevServerизhotдляtrue
  2. И вpluginsувеличить вnew webpack.HotModuleReplacementPlugin()
//webpack.config.js
const webpack = require('webpack');
module.exports = {
    //....
    devServer: {
        hot: true
    },
    plugins: [
        new webpack.HotModuleReplacementPlugin() //热更新插件
    ]
}

мы настроилиHotModuleReplacementPluginПозже вы обнаружите, что когда мы изменим код в это время, вся страница все равно будет обновлена. Я не хочу, чтобы вся страница обновлялась, и файл записи необходимо изменить:

  1. В файл записи добавлено:
if(module && module.hot) {
    module.hot.accept()
}

На этом этапе изменение кода не приведет к обновлению всей страницы.

6. Многостраничная упаковка приложения

Иногда наше приложение не обязательно одностраничное, а многостраничное, поэтому как использоватьwebpackУпакуйте это. Чтобы директория выглядела понятно, не создавайте отдельныйmapдокумент.

//webpack.config.js
const path = require('path');
const HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
    entry: {
        index: './src/index.js',
        login: './src/login.js'
    },
    output: {
        path: path.resolve(__dirname, 'dist'),
        filename: '[name].[hash:6].js'
    },
    //...
    plugins: [
        new HtmlWebpackPlugin({
            template: './public/index.html',
            filename: 'index.html' //打包后的文件名
        }),
        new HtmlWebpackPlugin({
            template: './public/login.html',
            filename: 'login.html' //打包后的文件名
        }),
    ]
}

Если вам нужно настроить несколькоHtmlWebpackPlugin,ТакfilenameПоле не может быть задано по умолчанию, в противном случае будет сгенерировано значение по умолчанию.index.html, если хотитеhtmlтакже есть в имени файлаhash, затем непосредственно изменитьflienameполя, например:filename: 'login.[hash:6].html'.

Сгенерированный каталог выглядит следующим образом:

.
├── dist
│   ├── 2.463ccf.js
│   ├── assets
│   │   └── thor_e09b5c.jpeg
│   ├── css
│   │   ├── index.css
│   │   └── login.css
│   ├── index.463ccf.js
│   ├── index.html
│   ├── js
│   │   └── base.js
│   ├── login.463ccf.js
│   └── login.html

Вроде бы все ок, но проверьтеindex.htmlа такжеlogin.htmlВыяснится, что оба введены одновременно.index.f7d21a.jsа такжеlogin.f7d21a.js, обычно это не то, чего мы хотим, надеемся,index.htmlтолько импортindex.f7d21a.js,login.htmlтолько импортlogin.f7d21a.js.

HtmlWebpackPluginпредоставилchunksПараметр может принимать массив.Настройка этого параметра приведет к импорту в html файл только тех js, которые указаны в массиве.Кроме того, если вам нужно импортировать несколько JS файлов и только несколько не хотите импортировать, вы также можете указатьexcludeChunksпараметр, который принимает массив.

//webpack.config.js
module.exports = {
    //...
    plugins: [
        new HtmlWebpackPlugin({
            template: './public/index.html',
            filename: 'index.html', //打包后的文件名
            chunks: ['index']
        }),
        new HtmlWebpackPlugin({
            template: './public/login.html',
            filename: 'login.html', //打包后的文件名
            chunks: ['login']
        }),
    ]
}

воплощать в жизньnpm run build, можно увидетьindex.htmlтолько представилindexизJSфайл, покаlogin.htmlтакже введен толькоloginизJSфайл, как мы и ожидали.

7. разрешить конфигурацию

resolveнастроитьwebpackКак найти файл, соответствующий модулю.webpackвстроенныйJavaScriptФункция разбора модульной грамматики будет найдена по умолчанию в правилах, согласованных в модульном стандарте, но вы можете изменить правила по умолчанию в соответствии со своими потребностями.

  1. modules

resolve.modulesнастроитьwebpackВ какие каталоги заходить для поиска сторонних модулей, по умолчанию заходить только вnode_modulesНайдите ниже, если у вас есть модуль в папке в нашем проекте, который часто импортируется и вы не хотите писать длинный путь, то вы можете настроитьresolve.modulesчтобы упростить.

//webpack.config.js
module.exports = {
    //....
    resolve: {
        modules: ['./src/components', 'node_modules'] //从左到右依次查找
    }
}

После этой конфигурации мыimport Dialog from 'dialog', буду искать./src/components/dialog, вам больше не нужно использовать относительные пути для импорта. если в./src/componentsЕсли вы не можете найти его, вы придетеnode_modulesИщите ниже.

  1. alias

resolve.aliasЭлемент конфигурации сопоставляет исходный путь импорта с новым путем импорта через псевдоним, например:

//webpack.config.js
module.exports = {
    //....
    resolve: {
        alias: {
            'react-native': '@my/react-native-web' //这个包名是我随便写的哈
        }
    }
}

Например, у нас есть зависимость@my/react-native-webможет быть реализованreact-nativeПеременаweb. Наш код обычно выглядит так:

import { View, ListView, StyleSheet, Animated } from 'react-native';

После настройки псевдонима при выходе в Интернет он будет изменен с@my/react-native-webНайдите соответствующие зависимости.

Конечно, если имя зависимости слишком длинное, вы также можете настроить для него более короткий псевдоним, который проще использовать, особенно сscopeупаковка.

  1. extensions

В проектах, адаптированных для нескольких терминалов, могут быть.web.js, .wx.js, например, в проекте переноса в сеть мы хотим найти первую.web.js, если нет, ищите.js. Мы можем настроить это так:

//webpack.config.js
module.exports = {
    //....
    resolve: {
        extensions: ['web.js', '.js'] //当然,你还可以配置 .json, .css
    }
}

Найдите первым../dialog.web.js, если он не существует, ищите../dialog.js. Это очень полезно при адаптации многотерминального кода, иначе нужно импортировать файлы под разные платформы (в ущерб скорости).

import dialog from '../dialog';

Конечно, настроитьextensions, мы можем использовать суффикс файла по умолчанию.Если в операторе импорта нет суффикса файла, он автоматически принесет его сextensionsПосле суффикса, настроенного в , попробуйте получить доступ, существует ли файл, поэтому поставьте высокочастотный суффикс впереди, а массив не должен быть слишком длинным, чтобы уменьшить количество попыток. Если не настроенextensions, по умолчанию будет найден только соответствующий файл js.

  1. enforceExtension

Если настроеноresolve.enforceExtensionдляtrue, то оператор импорта не может использовать суффикс файла по умолчанию.

  1. mainFields

Некоторые сторонние модули предоставляют несколько копий кода, напримерbootstrap, вы можете просмотретьbootstrapизpackage.jsonдокумент:

{
    "style": "dist/css/bootstrap.css",
    "sass": "scss/bootstrap.scss",
    "main": "dist/js/bootstrap",
}

resolve.mainFieldsКонфигурация по умолчанию['browser', 'main'], то есть сначала найти соответствующие зависимостиpackage.jsonсерединаbrowerполе, если нет, найтиmainполе.

Такие как:import 'bootstrap'По умолчанию соответствующие зависимости находятсяpackage.jsonизmainфайл, указанный полем, т.е.dist/js/bootstrap.

Допустим, мы желаем,import 'bootsrap'найти по умолчаниюcssфайл, вы можете настроитьresolve.mainFieldsдля:

//webpack.config.js
module.exports = {
    //....
    resolve: {
        mainFields: ['style', 'main'] 
    }
}

8. Различайте разные среды

До сих пор мыwebpackКонфигурация определяется вwebpack.config.jsВ случае необходимости различать среду разработки и производственную среду, мыprocess.env.NODE_ENVЧтобы различать конфигурацию, но если в файле конфигурации есть несколько конфигураций, которым нужно различать среду, это явно не лучший способ.

Лучшей практикой является создание нескольких файлов конфигурации, таких как:webpack.base.js,webpack.dev.js,webpack.prod.js.

  • webpack.base.jsопределить общую конфигурацию
  • webpack.dev.js: определяет конфигурацию среды разработки
  • webpack.prod.js: определяет конфигурацию производственной среды

webpack-mergeпредназначен дляwebpackпредназначен для обеспеченияmergeФункция для объединения массивов, объединения объектов.

npm install webpack-merge -D
const merge = require('webpack-merge');
merge({
    devtool: 'cheap-module-eval-source-map',
    module: {
        rules: [
            {a: 1}
        ]
    },
    plugins: [1,2,3]
}, {
    devtool: 'none',
    mode: "production",
    module: {
        rules: [
            {a: 2},
            {b: 1}
        ]
    },
    plugins: [4,5,6],
});
//合并后的结果为
{
    devtool: 'none',
    mode: "production",
    module: {
        rules: [
            {a: 1},
            {a: 2},
            {b: 1}
        ]
    },
    plugins: [1,2,3,4,5,6]
}

webpack.config.base.jsраспространен вwebpackнастроить наwebpack.config.dev.jsНапример, следующим образом:

//webpack.config.dev.js
const merge = require('webpack-merge');
const baseWebpackConfig = require('./webpack.config.base');

module.exports = merge(baseWebpackConfig, {
    mode: 'development'
    //...其它的一些配置
});

а затем изменить нашpackage.json, укажите соответствующийconfigдокумент:

//package.json
{
    "scripts": {
        "dev": "cross-env NODE_ENV=development webpack-dev-server --config=webpack.config.dev.js",
        "build": "cross-env NODE_ENV=production webpack --config=webpack.config.prod.js"
    },
}

вы можете использоватьmergeобъединить, вы также можете использоватьmerge.smartсливаться,merge.smartв слиянииloaderКогда одни и те же правила сопоставления объединяются,webpack-mergeПодробные примеры приведены в документации.

9. Определите переменные среды

Много раз мы будем использовать предварительную среду или локальное доменное имя в среде разработки и использовать онлайн-доменное имя в производственной среде.webpackОпределите переменные среды, а затем используйте их в своем коде.

использоватьwebpackВстроенный плагинDefinePluginдля определения переменных окружения.

DefinePluginКаждый ключ в , является идентификатором.

  • еслиvalueявляется строкой и будет рассматриваться какcodeФрагмент
  • еслиvalueне строка, будетstringify
  • еслиvalueЯвляется объектом, обычное определение объекта может быть
  • еслиkeyимеютtypeof, он нацелен только наtypeofопределение вызова
//webpack.config.dev.js
const webpack = require('webpack');
module.exports = {
    plugins: [
        new webpack.DefinePlugin({
            DEV: JSON.stringify('dev'), //字符串
            FLAG: 'true' //FLAG 是个布尔类型
        })
    ]
}
//index.js
if(DEV === 'dev') {
    //开发环境
}else {
    //生产环境
}

10. Используйте webpack для решения междоменных проблем

Предполагая, что передний конец находится на порту 3000, а сервер находится на порту 4000, мы проходимwebpackНастройте способ достижения междоменного доступа.

Сначала мы создаем локальныйserver.js:

let express = require('express');

let app = express();

app.get('/api/user', (req, res) => {
    res.json({name: '刘小夕'});
});

app.listen(4000);

выполнить код (run code), теперь мы можем получить доступ к этому интерфейсу в браузере:http://localhost:4000/api/user.

существуетindex.jsсредний запрос/api/user,Исправлятьindex.jsследующим образом:

//需要将 localhost:3000 转发到 localhost:4000(服务端) 端口
fetch("/api/user")
    .then(response => response.json())
    .then(data => console.log(data))
    .catch(err => console.log(err));

Мы надеемся получить доступ к интерфейсу 4000, настроив прокси.

Настроить прокси

ИсправлятьwebpackКонфигурация:

//webpack.config.js
module.exports = {
    //...
    devServer: {
        proxy: {
            "/api": "http://localhost:4000"
        }
    }
}

сделай это сноваnpm run dev, вы можете видеть, что консоль выводит{name: "刘小夕"}, чтобы достичь кросс-доменности.

В большинстве случаев интерфейс, предоставляемый серверной частью, не включает/api,который:/user,/info,/listПодождите, при настройке прокси мы не можем перечислить все API.

Измените наш серверный код и выполните его снова.

//server.js
let express = require('express');

let app = express();

app.get('/user', (req, res) => {
    res.json({name: '刘小夕'});
});

app.listen(4000);

Хотя внутренний интерфейс не содержит/api, когда мы запрашиваем внутренний интерфейс, мы по-прежнему используем/apiВ начале при настройке прокси убираем/api,Изменить настройку:

//webpack.config.js
module.exports = {
    //...
    devServer: {
        proxy: {
            '/api': {
                target: 'http://localhost:4000',
                pathRewrite: {
                    '/api': ''
                }
            }
        }
    }
}

сделай это сноваnpm run devДоступ в вашем браузере:http://localhost:3000/Консоль также печатает{name: "刘小夕"}, междоменный успех,

11. Данные внешнего моделирования

Простое моделирование данных

module.exports = {
    devServer: {
        before(app) {
            app.get('/user', (req, res) => {
                res.json({name: '刘小夕'})
            })
        }
    }
}

существуетsrc/index.jsпрямой запрос/userинтерфейс.

fetch("user")
    .then(response => response.json())
    .then(data => console.log(data))
    .catch(err => console.log(err));

Используйте интерфейс фиктивных данных Mocker-API

mocker-api создает фиктивные API для REST API. Это может быть полезно при тестировании приложений без реального сервера REST API.

  1. Установитьmocker-api:
npm install mocker-api -D
  1. Создайте новую папку mock в проекте и создайте новый файл mocker.js., файл выглядит следующим образом:
module.exports = {
    'GET /user': {name: '刘小夕'},
    'POST /login/account': (req, res) => {
        const { password, username } = req.body
        if (password === '888888' && username === 'admin') {
            return res.send({
                status: 'ok',
                code: 0,
                token: 'sdfsdfsdfdsf',
                data: { id: 1, name: '刘小夕' }
            })
        } else {
            return res.send({ status: 'error', code: 403 })
        }
    }
}
  1. Исправлятьwebpack.config.base.js:
const apiMocker = require('mocker-api');
module.export = {
    //...
    devServer: {
        before(app){
            apiMocker(app, path.resolve('./mock/mocker.js'))
        }
    }
}

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

  1. перезагружатьnpm run dev, вы можете видеть, что консоль успешно распечатана{name: '刘小夕'}
  2. Давайте изменим егоsrc/index.js, проверьте, успешно ли работает интерфейс POST
//src/index.js
fetch("/login/account", {
    method: "POST",
    headers: {
        'Accept': 'application/json',
        'Content-Type': 'application/json'
    },
    body: JSON.stringify({
        username: "admin",
        password: "888888"
    })
})
    .then(response => response.json())
    .then(data => console.log(data))
    .catch(err => console.log(err));

Вы можете увидеть успешные данные, возвращенные интерфейсом в консоли.

Это конец расширенной главы. Последняя глава — глава оптимизации. Принесите небольшую скамейку и семена дыни на встречу в следующий понедельник.

наконец

Если эта статья была вам полезна, пожалуйста, поставьте лайк этой статье.

Позвольте вам подробно разблокировать серию Webpack (оптимизация)

Обратите внимание на публичный аккаунт

掘金使用

Присоединяйтесь к группе технического обмена

Ссылаться на: