企业网站建设模块,深圳手机医疗网站建设,wordpress训网 插件,天津滨海新区天气预报一、webpack学习
简述
webpack是一个静态资源打包工具#xff0c;它会以一个或多个文件作为打包的入口#xff0c;将我们整个项目的文件编译组合成一个或多个文件输出出去。输出的文件就是编译好的文件#xff0c;可以运行在浏览器中。一般的我们将webpack输出的文件叫做b…一、webpack学习
简述
webpack是一个静态资源打包工具它会以一个或多个文件作为打包的入口将我们整个项目的文件编译组合成一个或多个文件输出出去。输出的文件就是编译好的文件可以运行在浏览器中。一般的我们将webpack输出的文件叫做bundle
为什么需要打包工具
随着现在前端技术的发展我们会使用各种框架Vue、ReactES6模块化语法、Less/Sass等css预处理器去提高新开发的效率和程序的健壮性。但是对于这些语法和框架我们的浏览器是不能直接运行的需要使用一些打包工具去将代码进行编译将其编译成浏览器可以运行的js、css等语法才能运行。
此外使用一些打包工具还可以压缩代码、做一些兼容性处理、提升代码的性能等。
常用打包工具
GulpWebpackVite…
功能
webpack有两种开发模式这两种开发模式的功能是有限的
开发模式只能编译js中的ES Module模块语法生产模式能编译js的ES Module模块语法和压缩js代码。所以要使用webpack去实现打包其他资源我们就需借助一些工具来实现。
Webpack五大核心模块
entry入口 指明了需要打包文件的入口让webpack知道从按个文件开始打包output 输出 指明了打包的文件要输出到哪里去并且如何命名等laoder加载器 由于webpack本身的功能很少只能解析js、json等资源所以在处于其他资源的时候就需要借助loaderwebpack才能解析plugins插件 就好比浏览器的插件一样可以扩展webpack的功能我们需要下载并且引用它mode模式 生产模式production 开发模式deveplopment
以上内容来自
Webpack基础篇(-)–入门
详细讲解
一、入口 entry
默认值是 ./src/index.js但你可以通过在 webpack configuration 中配置 entry 属性来指定一个或多个不同的入口起点。
webpack.config.js
module.exports {entry: {main: ./path/to/my/entry/file.js,},
};也可以简写为
module.exports {entry: ./path/to/my/entry/file.js,
};在你想要一次注入多个依赖文件并且将它们的依赖关系绘制在一个 “chunk” 中时我们就可以将一个文件路径数组传递给 entry 属性
webpack.config.js
module.exports {entry: [./src/file_1.js, ./src/file_2.js],output: {filename: bundle.js,},
};二、输出output
output 属性告诉 webpack 在哪里输出它所创建的 bundle以及如何命名这些文件。主要输出文件的默认值是 ./dist/main.js其他生成文件默认放置在./dist文件夹中。
webpack.config.js
const path require(path)module.exports {entry: ./path/to/my/entry/file.js,output: {path: path.resolve(__dirname,dist),filename: my-first-webpack.bundle.js}
}上面示例分别通过output.path和output.filename属性来设置文件输出位置以及输出文件的名称。
三、loader
webpack 只能理解 JavaScript 和 JSON 文件这是 webpack 开箱可用的自带能力。loader 让 webpack 能够去处理其他类型的文件并将它们转换为有效 模块以供应用程序使用以及被添加到依赖图中。
在更高层面在 webpack 的配置中loader 有两个属性
test 属性识别出哪些文件会被转换。use属性定义出在进行转换时应该使用哪个loader
注loader是在module下的rules属性下进行配置
webpack.confis.js
const path require(path)module.exports {entry: ,output: {path: ,filename: },module: {rules: [{test: /\.txt$/,use: raw-loader}],},
}以上配置中对一个单独的module对象定义了rules属性里面包含两个必须属性test和use。这告诉webpack编译器当遇到require或者import语句中被解析为 .txt的路径时在对它进行打包前先use使用raw-loader转换一下。
示例一
使用loader告诉webpack加载css文件或者将TypeScript转为JavaScript。为此首先安装相对应的loader。
npm install --save-dev css-loader ts-loader然后指示webpack对每个.css使用css-loader以及对所有的.ts文件使用ts-loader
webpack.config.js
module.exports {module: {relus: [{test: /\.css$/,use: css-loader},{test: /\.ts$/,use: ts-loader},]}
}示例二
module.rules允许你在webpack配置中指定多个loader。loader从左到右或从下到上的取值执行。在下面示例中从sass-loader开始执行将scss/sass文件编译成普通的css文件然后继续执行css-loadercss-loader会对css文件进行解析处理最后执行style-loaderstyle-loader会将css样式嵌入到html中。
module.exports {module: {rules: [{test: /\.css$/,use: [{loader: style-loader},{loader: css-loader,option: {modules: true // modules: true选项意味着它会将CSS类名转换为唯一的哈希值这样可以避免在项目中的CSS样式冲突。}},{loader: sass-loader}]}]}
}四、插件plugin
loader用于转换某些类型的模块而插件则可以用于执行范围更广的任务。包括打包优化资源管理注入环境变量。想要使用一个插件只需要require()它然后把它添加到plugin数组中多数插件可以通过选项option自定义。你也可以在一个配置文件中因为不同目的的而多次使用同一个插件这时要通过new操作符来创建一个插件实例。
webpack.config.js
const HtmlWebpackPlugin require(html-webpack-plugin);
const webpack require(webpack); // 访问内置的插件
const path require(path);module.exports {entry: ./path/to/my/entry/file.js,output: {filename: my-first-webpack.bundle.js,path: path.resolve(__dirname, dist),},module: {rules: [{test: /\.(js|jsx)$/,use: babel-loader,},],},plugins: [new webpack.ProgressPlugin(),new HtmlWebpackPlugin({ template: ./src/index.html }),],
};由于插件可以携带参数/选项你必须在 webpack 配置中向 plugins 属性传入一个 new 实例。
ProgressPlugin 用于自定义编译过程中的进度报告HtmlWebpackPlugin 将生成一个 HTML 文件并在其中使用 script 引入一个名为 my-first-webpack.bundle.js 的 JS 文件。
五、模式mode
通过选择developmentproduction或none之中的一个来设置mode参数你可以启用webpack内置在相应环境下的优化其默认值为production
module.exports {mode: production
}二、关于vue.config.js
简述
vue.config.js是一个可选的配置文件如果项目的根目录中存在这个文件那么它就会被vue/cli-service自动加载。你也可以使用package.json中的vue字段但是注意这种写法需要你严格遵守JSON的格式来写。
这个文件应该导出一个包含了选项的对象
vue.config.js
module.exports {// 选项
}vue.config.js
或者也可以使用vue/cli-service提供的defineConfig帮手函数以获得更好的类型提示
const { defineConfig } require(vue/cli-service)module.exports defineConfig({// 选项
})vue.config.js的配置项
publicPath 部署时的基本 URL 类型string 默认值“/” 用法和 webpack 本身的 output.publicPath 一致但是 Vue CLI 在一些其他地方也需要用到这个值所以请始终使用 publicPath 而不要直接修改 webpack 的 output.publicPath。 默认情况下vue-cli 会假设你的应用是被部署在一个域名的根路径上例如https://www.baidu.com/。如果部署在一个子路径上你就需要用这个选项指定这个子路径。例如你要部署在https://www.baidu.com/other/则设置publicPath为/other/。 publicPath这个值也可以设置为 或是相对路径 ./ ,这样所有的资源都会被链接为相对路径这样打出来的包可以被部署在任意路径。
vue.config.js
// 这个值在开发环境下同样生效module.exports {publicPath: process.env.NODE_ENV production? /production-sub-path/: /
}outputDir 打包后生成的文件夹目录 类型 string 默认值dist 当运行vue-cli-service build时生成的生产环境构建文件的目录。注意目标目录在构建之前会被清除构建时传入--no-clean可关闭该行为
assetsDir 放置生成的静态资源的目录 类型string 默认值‘’ 放置生成的静态资源js、css、img、fonts的相对于outputDir的目录
indexPath 生成的index.html的输出路径 类型string 默认值 index.html 指定生成的 index.html 的输出路径 (相对于 outputDir)。也可以是一个绝对路径。
finenameHashing 文件名是否包含哈希 类型string 默认值true 默认情况下生成的静态资源在它们的文件名中包含了hash以便更好的控制缓存。然而这也要求index的html是被vue cli自动生成的。如果你无法使用vue cli生成index html你可以通过将这个选项设为false来关闭文件名哈希。
productionSourceMap
类型boolean默认值true如果你不需要生产环境的source map可以将其设置为false以加速生产环境构建。
pages
类型object默认值 undefind在multi-page模式下构建应用每个page应该有一个对应的JavaScript入口文件。其值应该是一个对象对象的key是入口的名字value是一个指定了entry、template、filename、title和chunks的对象除了entry之外都是可选的或一个指定其entry的字符串
vue.config.js
module.exports {pages: {index: {// page 的入口entry: src/index/main.js,// 模板来源template: public/index.html,// 在 dist/index.html 的输出filename: index.html,// 当使用 title 选项时// template 中的 title 标签需要是 title% htmlWebpackPlugin.options.title %/titletitle: Index Page,// 在这个页面中包含的块默认情况下会包含// 提取出来的通用 chunk 和 vendor chunk。chunks: [chunk-vendors, chunk-common, index]},// 当使用只有入口的字符串格式时// 模板会被推导为 public/subpage.html// 并且如果找不到的话就回退到 public/index.html。// 输出文件名会被推导为 subpage.html。subpage: src/subpage/main.js}
}css相关配置
Vue CLI 项目天生支持 PostCSS、CSS Modules 和包含 Sass、Less、Stylus 在内的预处理器。
1、引用静态资源
所有编译后的 CSS 都会通过 css-loader 来解析其中的 url() 引用并将这些引用作为模块请求来处理。这意味着你可以根据本地的文件结构用相对路径来引用静态资源。另外要注意的是如果你想要引用一个 npm 依赖中的文件或是想要用 webpack alias则需要在路径前加上 ~ 的前缀来避免歧义。
2、预处理器
你可以在创建项目的时候选择预处理器 (Sass/Less/Stylus)。如果当时没有选好内置的 webpack 仍然会被预配置为可以完成所有的处理。你也可以手动安装相应的 webpack loader
// Sass
npm install -D sass-loader sass// Less
npm install -D less-loader less// Stylus
npm install -D stylus-loader stylus然后你就可以导入相应的文件类型或在 *.vue 文件中这样来使用
style langscss$color: red;
/style自动化导入
如果你想自动化导入文件 (用于颜色、变量、mixin……)你可以使用 style-resources-loader。这里有一个关于 Stylus 的在每个单文件组件和 Stylus 文件中导入 ./src/styles/imports.styl 的例子
// vue.config.jsconst path require(path)module.exports {chainWebpack: config {const types [vue-modules, vue, normal-modules, normal]types.forEach(type addStyleResource(config.module.rule(stylus).oneOf(type)))},
}function addStyleResource (rule) {rule.use(style-resource).loader(style-resources-loader).options({patterns: [path.resolve(__dirname, ./src/styles/imports.styl),],})
}PostCSS
你可以通过 .postcssrc 或任何 postcss-load-config 支持的配置源来配置 PostCSS。也可以通过 vue.config.js 中的 css.loaderOptions.postcss 配置 postcss-loader。
CSS Modules
如果你希望自定义生成的 CSS Modules 模块的类名可以通过 vue.config.js 中的 css.loaderOptions.css 选项来实现。所有的 css-loader 选项在这里都是支持的例如 localIdentName 和 camelCase
// vue.config.jsmodule.exports {css: {loaderOptions: {css: {// 注意以下配置在 Vue CLI v4 与 v3 之间存在差异。// Vue CLI v3 用户可参考 css-loader v1 文档// https://github.com/webpack-contrib/css-loader/tree/v1.0.1modules: {localIdentName: [name]-[hash]},localsConvention: camelCaseOnly}}}
}或
css: {extract: {// 打包后css文件名称添加时间戳filename: css/[name].${timeStamp}.css,chunkFilename: css/chunk.[id].${timeStamp}.css},loaderOptions: {less: {modifyVars: {/* less 变量覆盖用于自定义 ant design 主题 */primary-color: #1890FF,link-color: #1890FF,border-radius-base: 4px,layout-color: #9867f7},javascriptEnabled: true}}},向预处理器 Loader 传递选项
有的时候你想要向 webpack 的预处理器 loader 传递选项。你可以使用 vue.config.js 中的 css.loaderOptions 选项。比如你可以这样向所有 Sass/Less 样式传入共享的全局变量
// vue.config.js
module.exports {css: {loaderOptions: {// 给 sass-loader 传递选项sass: {// / 是 src/ 的别名// 所以这里假设你有 src/variables.sass 这个文件// 注意在 sass-loader v8 中这个选项名是 prependDataadditionalData: import ~/variables.sass},// 默认情况下 sass 选项会同时对 sass 和 scss 语法同时生效// 因为 scss 语法在内部也是由 sass-loader 处理的// 但是在配置 prependData 选项的时候// scss 语法会要求语句结尾必须有分号sass 则要求必须没有分号// 在这种情况下我们可以使用 scss 选项对 scss 语法进行单独配置scss: {additionalData: import ~/variables.scss;},// 给 less-loader 传递 Less.js 相关选项less:{// http://lesscss.org/usage/#less-options-strict-units Global Variables// primary is global variables fields nameglobalVars: {primary: #fff}}}}
}devServer
类型Object所有webpack-dev-server的选项都支持注意有些值像host、port和https可能会被命令行参数覆写有些值像publicPath和historyApiFallback不应该被改写因为它们需要和开发服务器的publicpath同步以保障正常的工作。
devServer.proxy dev环境下webpack-dev-server相关配置 类型string/Object 如果你的前端应用和后端API服务器没有运行在同一个主机上你需要在开发环境下将API请求代理到API服务器。这个问题可以通过vue.config.js中的devServer.proxy选项来配置。
devServer.proxy可以是一个指向开发环境API服务器的字符串
module.exports {devServer: {proxy: http://localhost:4000}
}module.exports {devServer: {proxy: {port: 8090,host: 0.0.0.0,https: false,open: true,}}
}port开发运行时的端口host开发运行时域名设置成 0.0.0.0 在同一个局域网下如果你的项目在运行同时可以通过你的 http://ip:port/...访问你的项目https是否启用httpsopennpm run serve 时是否直接打开浏览器
这会告诉开发服务器将任何未知请求没有匹配到静态文件的请求代理到http://localhost:4000
如果你想要更多的代理控制行为也可以使用一个 path: options 成对的对象。完整的选项可以查阅 http-proxy-middleware 。
module.exports {
// 反向代理devServer: {index: /login.html, // 默认打开文件open: true, // 自动打开浏览器host: localhost, // 默认打开域名port: 8080, // 默认打开端口号https: false, // 开启关闭https请求hotOnly: false, // 热更proxy: {// 配置跨域/api: {target: http://dev.aabb.cn:8082/, // 代理地址这里设置的地址会代替axios中设置的baseURLws: true, // proxy websocketschangeOrigin: true, // 如果接口跨域需要进行这个参数配置pathRewrite: { // pathRewrite方法重写url^/api: /,},},},},
} 示例
vue.config.js
module.exports {publicPath: ./, // 公共路径 默认为/建议使用./相对路径devServer: { // 本地服务器配置(npm run serve)port: 8080, // 端口host: localhost, // 域名https: false, // 是否开启httpsopen: true // 是否在开启服务器后自动打开浏览器访问该服务器},lintOnSave: false, // 取消lint语法检测此处可不配置outputDir:dist, // build打包输出目录assetsDir:assets, // 静态文件输出目录基于distindexPath: index.html, // 输出html文件名productionSourceMap: false, // 取消.map文件的打包加快打包速度configureWebpack: (config) {// process.env为环境变量分别对应.env.development文件和.env.production文件 此处表示加快开发环境打包速度if (process.env.NODE_ENV ! production) return;config.optimization.minimizer[0].options.terserOptions.compress.drop_console false; //生产环境去掉console.logreturn { // 此处配置webpack.config.js的相关配置plugins: [],performance: {}};}
};插件及规则的配置
在vue.config.js如果要新增/修改webpack的plugins或者rules有两种方式。
configgureWebpack方式
configgureWebpack 是相对比较简单的一种方式它可以是一个对象和webpack本身配置方式一致该对象将会被webpack-merge 合并入最终的webpack配置它也可以是一个函数直接在函数内部进行修改配置
module.exports {configureWebpack: {rules: [],plugins: [new MyAwesomeWebpackPlugin()]}
}configureWebpack: (config) {// 例如通过判断运行环境设置modeconfig.mode production
}chainWebpack方式
chainWebpack是一个函数会接收一个基于 webpack-chain 的 ChainableConfig 实例。允许对内部的 webpack 配置进行更细粒度的修改。chainWebpack 链式操作高级接下来所有的配置都会在该选项中进行配置。
三、webpack-chain的使用
简述
通过链式的方式修改webpack的配置
使用
entry 和 output
module.exports {chainWebpack: config {config.entryPoints.clear() // 把默认的入口清空config.entry(entry1).add(./src/index1.tsx) // 新增入口config.entry(entry2).add(./src/index2.tsx) // 新增文件config.output.path(dist).filename([name].[chunkhash].js).chunkFilename(chunks/[name].[chunkhash].js).libraryTarget(umd)}
}alias
对于路径别名的配置配置如下
module.exports {chainWebpack: config {config.resolve.alias.set(assets,resolve(src/assets)).set(components,resolve(src/components)).set(static,resolve(src/static)).delete(static) // 删掉指定的别名}
}loader
1、添加一个loader
module.exports {chainWebpack: config {config.module.rule(name).use(name).loader(loader).option(option)}
}示例
module.exports {chainWebpack: config {config.module.rules(ts).test(/\.tsx?/).use(ts-loader).loader(ts-loader).option({transpileOnly: true}).end()}
}2、修改loader参数
可通过tap方法修改loader的参数
module.exports {chainWebpack: config {config.module.rule(ts).test(/\.tsx?/).use(ts-loader).loader(ts-loader).tap(option {// do some ...return option}).end()}
}在所有的配置完成之后可以通过调用config.toConfig()来拿到最后的配置对象可以直接作为webpack的配置。
3、移除一个loader
通过uses对象的delete方法根据loader的name删除
module.exports {chainwebpack: config {config.module.rule(ts).test(/\.tsx?/).uses.delete(ts-loader)}
}plaugin
1、添加一个插件
先指定名字这个名字是自定义的然后通过 use 添加插件use的第一个参数是插件名称第二个参数是插件参数这个参数必须是一个数组也可以不传。
// vue.config.jsmodule.exports {chainWebpack: config {config.plugin(name).use(WebpackPlugin, args)}
}示例
const ExtractTextPlugin require(extract-text-webpack-plugin);module.exports {chainWebpack: config {config.plugin(extract).use(ExtractTextPlugin, [{filename: build.min.css,allChunks: true,}])}
}2、移除插件
添加插件时我们自定义了一个插件name移除插件就是通过这个name来进行实现的
module.exports {chainWebpack: config {config.plugins.delete(extract)}
}3、指定插件在xx插件之前/之后凋用
例如现在需要指定 html-webpack-plugin 这个插件在刚刚写的 extract 插件之前执行则写法如下
const htmlWebpackPlugin require(html-webpack-plugin)module.exports {chainWebpack: config {config.plugin(html).use(htmlWebpackPlugin).before(extract)}
}通过 before 方法传入另一个插件的 name 即可表示在另一个插件之前执行。
同样如果需要在 extract 插件之后执行调用 after 方法
const htmlWebpackPlugin require(html-webpack-plugin)module.exports {chainWebpack: config {config.plugin(html).use(htmlWebpackPlugin).after(extract)}
}4、动态修改插件参数
我们可以用 webpack-chain 来动态修改插件的传参举例如下使用tap方法修改参数
module.exports {chainWebpack: config {config.plugin(name).use(webpackPluginName).tap(args newArgs)}
}5、修改插件初始化过程
我们可以自定义插件的实例化的过程比如下面这样通过init方法返回一个实例这将代替原有的实例化过程
module.exports {chainWebpack: config {config.plugin(name).init((Plugin, args) new Plugin(...args));}
}