本文中的例子支持webpack-dev-server自动刷新及react热替换,使用了redux管理state,用react-router切换路由,用babel实现ES6语法书写,同时支持async/await书写,eslint代码检测,及sass的使用
1.搭建前文档结构:
assets 用来存放css 及 图片等资源
components存放组件
js 用来存放js文件
页面主文件是 index.html
不用纠结文件夹结构,只要不涉及团队合作,这玩意儿就像自己的女人,想咋睡咋睡,想咋组织就咋组织 大致如此
2.webpack配置文件的书写
var webpack=require('webpack');var path=require('path');var DashboardPlugin = require('webpack-dashboard/plugin');//一款很屌的插件,用了你就知道了module.exports={ entry:{ //多文件入口以及配置dev server及热替换 app:[path.resolve(__dirname, './js/index.js'),'webpack/hot/dev-server.js','webpack-dev-server/client?http://0.0.0.0:8080'], vendor:['react'] }, output:{ //多文件输出 注意[name]这种写法 publicPath:'/build', filename:'[name].js' }, module:{ loaders:[ //最新loader的写法 {test:/\.js?$/,loaders:['babel','eslint'],exclude: /node_modules/}, {test:/\.jsx?$/,loaders:['babel','eslint'],exclude: /node_modules/}, {test: /\.(jpg|png|gif)$/, loader: "url?limit=8192",exclude: /node_modules/}, {test:/\.(scss|css)?$/,loader:'style!css!sass',exclude: /node_modules/} ] }, resolve:{ //配置node_modules的地址、文件名省略及文件路径简写 root:'/Users/****/mywork/rwp/node_modules', extensions:['','.js','.jsx','.json','.scss'], alias:{ listCss:path.join(__dirname,'./assets/css/list'), publicCss:path.join(__dirname,'./assets/css/public'), bkCss:path.join(__dirname,'./assets/css/bk'), coverCss:path.join(__dirname,'./assets/css/cover'), listCp:path.join(__dirname,'./components/list'), bkCp:path.join(__dirname,'./components/bk'), cbCp:path.join(__dirname,'./components/cb'), publicCp:path.join(__dirname,'./components/public'), coverCp:path.join(__dirname,'./components/cover') } }, eslint:{ //eslint配置文件 configFile:"./.eslintrc.js" }, plugins:[ new webpack.NoErrorsPlugin(), //防错误打断程序插件 new DashboardPlugin(), new webpack.optimize.CommonsChunkPlugin('vendor', 'vendor.js') ]}
以上是webpack.config.js,用于生产环境的配置文件,下面这个是一个比较粗糙的生产环境配置文件,待优化
var webpack=require('webpack');var path=require('path');var uglifyJsPlugin = webpack.optimize.UglifyJsPlugin;//代码压缩插件var CopyWebpackPlugin = require('copy-webpack-plugin');//文件拷贝插件module.exports={ entry:{ "./build/app":path.resolve(__dirname, './js/index.js'), "./build/vendor":['react'] }, output:{ publicPath:'/', path:path.resolve(__dirname,'../../package'), filename:'[name].js' }, module:{ loaders:[ {test:/\.js?$/,loaders:['babel','eslint'],exclude: /node_modules/}, {test:/\.jsx?$/,loaders:['babel','eslint'],exclude: /node_modules/}, {test: /\.(jpg|png|gif)$/, loader: "url?limit=8192",exclude: /node_modules/}, {test:/\.(scss|css)?$/,loader:'style!css!sass',exclude: /node_modules/} ] }, resolve:{ root:'/Users/****/mywork/rwp/node_modules', extensions:['','.js','.jsx','.json','.scss'], alias:{ listCss:path.join(__dirname,'./assets/css/list'), publicCss:path.join(__dirname,'./assets/css/public'), bkCss:path.join(__dirname,'./assets/css/bk'), coverCss:path.join(__dirname,'./assets/css/cover'), listCp:path.join(__dirname,'./components/list'), bkCp:path.join(__dirname,'./components/bk'), cbCp:path.join(__dirname,'./components/cb'), publicCp:path.join(__dirname,'./components/public'), coverCp:path.join(__dirname,'./components/cover') } }, plugins:[ new webpack.optimize.DedupePlugin(),//文件内容深度去重 new uglifyJsPlugin({ compress: { warnings: false } }), new CopyWebpackPlugin([ { from: 'index.html', to: 'index.html' } ]) ]}
关于配置文件的详细叙述及各字段意思请大家查看官网:
下面是package.json
{ "name": "rwp", "version": "1.0.0", "description": "this is a test project", "main": "server.js", "scripts": { "build": "webpack --progress --profile --colors --config webpack.production.config.js", "start": "webpack-dashboard -- webpack-dev-server --hot --progress --colors" }, "keywords": [ "test" ], "babel": { "presets": [ "es2015", "react" ] }, "author": "jhone lee", "license": "ISC", "dependencies": { "babel-runtime": "^6.11.6", "body-parser": "1.15.x", "copy-webpack-plugin": "^3.0.1", "express": "4.x", "jquery": ">=2.x", "react": ">=15.2.x", "react-redux": "^4.4.5", "react-router": "2.6.x", "react-router-redux": "^4.0.5", "redux": "^3.5.2", "redux-logger": "^2.6.1", "redux-thunk": "^2.1.0" }, "devDependencies": { "babel": "6.x", "babel-core": "6.x", "babel-eslint": "^6.1.2", "babel-loader": "*", "babel-plugin-transform-runtime": "^6.12.0", "babel-polyfill": "^6.13.0", "babel-preset-es2015": "^6.9.0", "babel-preset-react": "^6.11.1", "babel-preset-stage-0": "^6.5.0", "babel-runtime": "^6.11.6", "css-loader": "*", "eslint": "^3.3.1", "eslint-loader": "^1.5.0", "eslint-plugin-react": "^5.2.2", "file-loader": "^0.9.0", "jsx-loader": "^0.13.2", "node-sass": "^3.8.0", "react-dom": "^15.2.1", "redux": "^3.5.2", "redux-devtools": "^3.3.1", "sass-loader": "^4.0.0", "style-loader": "^0.13.1", "url-loader": "^0.5.7", "webpack": "1.13.1", "webpack-dashboard": "^0.1.7", "webpack-dev-server": "1.4.x" }}
这里需要注意的script里面需要执行的命令:
npm run build 会运行生产环境的config文件
npm start 会运行开发环境的config文件
后面至于 redux及react-router怎么用,以及.babelrc 和 .eslintrc怎么配置不在本文的讨论范畴
仅粘出我的 两个rc文件module.exports = { "parser":"babel-eslint", "env": { "browser": true, "commonjs": true, "es6": true }, "extends": "eslint:recommended", "parserOptions": { "ecmaFeatures": { "experimentalObjectRestSpread": true, "jsx": true }, "sourceType": "module" }, "plugins": [ "react" ], "rules": { "indent": [ "warn", 4 ], "linebreak-style": [ "warn", "unix" ], "quotes": [ "warn", "double" ], "semi": [ "error", "always" ], "no-unused-vars":[ "warn", { "vars": "all", "args": "after-used" } ], "no-console":[ "error",{ "allow":["log","error","warn"] }], "no-constant-condition":[ "warn",{ "checkLoops":false } ], "no-fallthrough":["warn",{ "commentPattern": "break[\\s\\w]*omitted" }] }};
以上为 .eslintrc
{ "presets": [ "es2015", "stage-0","react"], "plugins": [ ["transform-runtime", { "polyfill": false, "regenerator": true }] ]}
以上为 .babelrc
至于react-router及redux怎么用,以后有时间再说