zoukankan      html  css  js  c++  java
  • vue-hackernews-2.0 升级到 webpack4 和 nodejs14 的坑(上)

    概述

    最近非常想做一个服务端渲染项目,那就打算从尤大的vue-hackernews-2.0开始入手呗。其实我之前试图改造过这个项目,但是因为当时很菜所以失败了。现在我觉得有能力改造好,那就开始呗。把心得记录下来,供以后开发时参考,相信对其他人也有用。

    mode

    webpack4带来的第一个大变化就是增加了mode字段来区分生产环境还是开发环境,所以我们到webpack.base.config.js里面去增加mode字段:

    mode: isProd ? 'production' : 'development',
    

    package.json

    老项目的依赖如下:

    "dependencies": {
        "compression": "^1.7.1",
        "cross-env": "^5.1.1",
        "es6-promise": "^4.1.1",
        "express": "^4.16.2",
        "extract-text-webpack-plugin": "^3.0.2",
        "firebase": "4.6.2",
        "lru-cache": "^4.1.1",
        "route-cache": "0.4.3",
        "serve-favicon": "^2.4.5",
        "vue": "^2.5.22",
        "vue-router": "^3.0.1",
        "vue-server-renderer": "^2.5.22",
        "vuex": "^3.0.1",
        "vuex-router-sync": "^5.0.0"
    },
    "devDependencies": {
        "autoprefixer": "^7.1.6",
        "babel-core": "^6.26.0",
        "babel-loader": "^7.1.2",
        "babel-plugin-syntax-dynamic-import": "^6.18.0",
        "babel-preset-env": "^1.6.1",
        "chokidar": "^1.7.0",
        "css-loader": "^0.28.7",
        "file-loader": "^1.1.5",
        "friendly-errors-webpack-plugin": "^1.6.1",
        "extract-text-webpack-plugin": "^3.0.2",
        "rimraf": "^2.6.2",
        "stylus": "^0.54.5",
        "stylus-loader": "^3.0.1",
        "sw-precache-webpack-plugin": "^0.11.4",
        "url-loader": "^0.6.2",
        "vue-loader": "^15.3.0",
        "vue-template-compiler": "^2.5.22",
        "webpack": "^3.8.1",
        "webpack-dev-middleware": "^1.12.0",
        "webpack-hot-middleware": "^2.20.0",
        "webpack-merge": "^4.2.1",
        "webpack-node-externals": "^1.7.2"
    }
    

    我们删除一下插件,用更新的插件来代替他:

    // 删除
    "babel-core": "^6.26.0",
    "extract-text-webpack-plugin": "^3.0.2",
    
    // 添加
    "@babel/cli": "^7.11.6",
    "@babel/core": "^7.11.6",
    "@babel/preset-env": "^7.11.5",
    "mini-css-extract-plugin": "^1.0.0",
    
    // webpack4 需要安装 webpack-cli
    "webpack-cli": "^3.3.12",
    

    然后重新安装所有其它依赖,让它们达到最新版本。

    firebase

    尤大的这个项目是使用 firebase 来获取 hackernews 的数据的,我本来想用 axios 取代的,但是我去看了一下hackernews 的 api之后发现,尤大的 firebase 的写法只需要少量代码就能够获取全部数据,如果使用 axios 的话,就需要先去请求一个总接口获取文章 id,然后再用这些 id 去一篇篇获取每篇文章的数据,非常麻烦,所以这里就没有升级到 axios。

    另外,我去看了一下最新版本的 firebase 的 api,发现使用方法和尤大那个版本的使用方法是一样的,所以这里只需要升级 firebase 到最新版本即可。

    lru-cache

    lru-cache 升级到最新版本之后需要使用 new 语法:

    // 旧的语法
    api.cachedItems = LRU({
        max: 1000,
        maxAge: 1000 * 60 * 15 // 15 min cache
    })
    
    // 新的语法
    api.cachedItems = new LRU({
        max: 1000,
        maxAge: 1000 * 60 * 15 // 15 min cache
    })
    

    babel

    老项目使用的 babel-core 现在已经不建议使用了,用@babel/preset-env替代,然后在 babel-loader 的 presets 里面加入@babel/preset-env

    {
        test: /.js$/,
        loader: 'babel-loader',
        exclude: /node_modules/,
        options: {
            presets: ['@babel/preset-env']
        }
    }
    

    css

    webpack4 摈弃了 extract-text-webpack-plugin 而使用新的 mini-css-extract-plugin 插件,我们注释掉上一个插件的代码,然后使用新的 mini-css-extract-plugin 插件。

    但是这个插件有一个问题,就是它在 extract css 文件的时候会使用 document 方法,从而导致 ssr 的服务端打包的时候会报document is not defined的错误,具体可以看这里

    解决方案推荐使用 null-loader,原理是在服务端打包的时候,不处理 css,这就要求客户端和服务端使用不同的配置,代码如下:

    // webpack.client.config.js
    module: {
        rules: [
          {
            test: /.styl(us)?$/,
            use: [
              isProd ? {
                loader: MiniCssExtractPlugin.loader,
                options: {
                  esModule: false,
                },
              } : 'vue-style-loader',
              {
                loader: 'css-loader',
                options: {
                  esModule: false,
                }
              },
              'stylus-loader'
            ],
          },
        ],
    }
    plugins: [
        new MiniCssExtractPlugin({
          filename: 'common.[chunkhash].css'
        }),
    ]
    
    // webpack.server.config.js
    module: {
        rules: [
          {
            test: /.styl(us)?$/,
            use: 'null-loader'
          }
        ]
    },
    

    由于此项目是使用 stylus 的,所以如果使用 scss 等的话可以类似处理。

  • 相关阅读:
    工单组件增强
    一些BAPI
    实例程序
    使用BAPI一定要提交和回滚(错误)
    动态内表值导出为TXT文件
    网页常用功能
    Code Complete
    Typescript 解构 、展开
    Typescript变量声明
    TypeScript基础数据类型
  • 原文地址:https://www.cnblogs.com/yangzhou33/p/13800189.html
Copyright © 2011-2022 走看看