@craco/craco copia la configuración del proyecto cra

Alias ​​de ruta (alias)

const webpackConfig = {
      webpack: {
        alias: {
          '@': path.resolve(__dirname, 'src'), // 配置src别名
        },
    }
}
module.export = webpackConfig

Modificar el nombre de la carpeta del producto empaquetado.

El nombre predeterminado de la carpeta de productos empaquetados de cra es build. Habitualmente lo llamamos dist.

Se deben escribir las dos líneas clave:

rutas.appBuild = 'dist'

ruta: ruta.resolve(__dirname, 'dist')

const webpackConfig = {
    webpack: {
        configure: (webpackConfig, { env, paths }) => {
          paths.appBuild = 'dist' // 修改打包输出文件目录
          webpackConfig.output = {
            ...webpackConfig.output,
            path: path.resolve(__dirname, 'dist'), // 修改打包输出文件目录 两步都要写
            publicPath: whenProd(() => '/', '/'), // 静态资源publicpath
              }
          }
        })
    }
}

CDN de referencia de la biblioteca de producción

cra tiene un complemento HtmlWebpackPlugin incorporado. Puede usar directamente el método getPlugin de cra para obtener la instancia del complemento.

const { getPlugin, pluginByName, whenProd } = require('@craco/craco')
const webpackConfig = {
    webpack: {
        configure((config,{env, paths})){
             // 线上替换cdn key:value key为库的名字 value为umd模块导出到global对象的key名
      whenProd(() => {
        webpackConfig.externals = {
          react: 'React',
          'react-dom': 'ReactDOM',
          history: 'History',
          'react-router-dom': 'ReactRouterDOM',
          redux: 'Redux',
          'react-redux': 'ReactRedux',
          dayjs: 'dayjs',
          antd: 'antd',
          axios: 'axios',
          '@ant-design/icons': 'icons',
        }
      })
      // 根据插件名获取插件 返回是否找到和匹配的插件
      const { isFound: isHtmlWebpackPluginFound, match: htmlWebpackPlugin } =
        getPlugin(webpackConfig, pluginByName('HtmlWebpackPlugin'))
      if (isHtmlWebpackPluginFound) {
        htmlWebpackPlugin.userOptions.title = whenProd(
          () => '后台管理系统-生产环境',
          '后台管理系统-开发环境'
        )
        // cdnurl要按照库的相互依赖优先级填写 被依赖的写前面优先加载
        htmlWebpackPlugin.userOptions.cdn = whenProd(
          () => ({
            js: [
              'https://cdn.bootcdn.net/ajax/libs/react/18.2.0/umd/react.production.min.js',
              'https://cdn.jsdelivr.net/npm/[email protected]/umd/react-router-dom.min.js',
              'https://cdnjs.cloudflare.com/ajax/libs/history/4.9.0/history.min.js',
              'https://cdn.bootcdn.net/ajax/libs/react-dom/18.2.0/umd/react-dom.production.min.js',
              'https://cdn.bootcdn.net/ajax/libs/redux/4.2.0/redux.min.js',
              'https://cdn.bootcdn.net/ajax/libs/react-redux/8.0.5/react-redux.min.js',
              'https://cdn.bootcdn.net/ajax/libs/dayjs/1.11.7/dayjs.min.js',
              'https://cdn.bootcdn.net/ajax/libs/antd/5.1.6/antd.min.js',
              'https://cdn.bootcdn.net/ajax/libs/axios/1.2.5/axios.min.js',
              'https://cdn.bootcdn.net/ajax/libs/ant-design-icons/5.0.1/index.umd.min.js',
            ],
            css: ['https://cdn.bootcdn.net/ajax/libs/antd/5.1.6/reset.min.css'],
          }),
          // 本地环境设为空 防止页面遍历报错
          {
            js: [],
            css: [],
          }
        )
      }
            return webpackConfig
        }
    }
}
module.exports = webpackConfig;

El recorrido de la plantilla HTML genera etiquetas: 

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <link rel="icon" href="%PUBLIC_URL%/favicon.ico" />
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <meta name="theme-color" content="#000000" />
    <meta
      name="description"
      content="Web site created using create-react-app"
    />
    <link rel="apple-touch-icon" href="%PUBLIC_URL%/logo192.png" />
    <!--
      manifest.json provides metadata used when your web app is installed on a
      user's mobile device or desktop. See https://developers.google.com/web/fundamentals/web-app-manifest/
    -->
    <link rel="manifest" href="%PUBLIC_URL%/manifest.json" />
    <!--
      Notice the use of %PUBLIC_URL% in the tags above.
      It will be replaced with the URL of the `public` folder during the build.
      Only files inside the `public` folder can be referenced from the HTML.

      Unlike "/favicon.ico" or "favicon.ico", "%PUBLIC_URL%/favicon.ico" will
      work correctly both with client-side routing and a non-root public URL.
      Learn how to configure a non-root public URL by running `npm run build`.
    -->
    <!-- js表达式写在<\%表达式\%> 渲染变量<\%=变量l\%> 这里的\是为了转义百分号防止webpack报错-->
    <% htmlWebpackPlugin.options.cdn.css.forEach(cdnUrl => { %>
    <link rel="stylesheet" href="<%= cdnUrl %>" />
    <% }) %>
    <title><%= htmlWebpackPlugin.options.title %></title>
  </head>
  <body>
    <noscript>您的浏览器不支持JavaScript 请开启JavaScript再浏览</noscript>
    <div id="root"></div>
  </body>
  <% htmlWebpackPlugin.options.cdn.js.forEach(cdnUrl => { %>
  <script type="text/javascript" src="<%= cdnUrl %>"></script>
  <% }) %>
</html>

Compresión gzip (NGINX necesita habilitar la descompresión gzip)

Primero instale el complemento de compresión compresión-webpack-plugin:

hilo agregar compresión-webpack-plugin -D

const CompressionWebpackPlugin = require('compression-webpack-plugin')
const webpackConfig = {
    webpack: {
        configure(webpackConfig, { env, paths }){
          // 使用gzip压缩超过1M的js和css文件
          webpackConfig.plugins.push(
            new CompressionWebpackPlugin({
              algorithm: 'gzip',
              test: /\.(js|css)$/,
              threshold: 1024,
              minRatio: 0.8,
            })
          )
          return webpackConfig
        }
    }
}
module.exports = webpackConfig;

Mezclar archivos scss globales

Utilice el complemento craco-sass-resources-loader para procesar scss global, instálelo primero:

hilo agregar craco-sass-resources-loader -D

const sassResourcesLoader = require('craco-sass-resources-loader')
const webpackConfig = {
    plugins: [
    {
      plugin: sassResourcesLoader, // 在所有scss文件加载前加载 全局加载到前面
      options: {
        // 配置多个文件 传文件的绝对路径
        resources: [
          path.resolve(__dirname, 'src', 'styles', 'common.module.scss'),
          path.resolve(
            __dirname,
            'src',
            'styles',
            'global-variables.module.scss'
          ),
          path.resolve(__dirname, 'src', 'styles', 'antd.module.scss'),
        ],
      },
    },
  ],
}
module.exports = webpackConfig;

 Modificar el puerto del servidor de desarrollo

const webpackConfig = {
    devServer: {
        port: 8421,
    }
}
module.exports = webpackConfig;

Analizar el volumen de paquetes js empaquetados.

Instale el complemento source-map-explorer (complemento recomendado por el documento oficial de cra) y un complemento de visualización colorido: webpack-bundle-analyzer, instale el complemento

hilo agregar explorador-mapa-fuente -D

script de configuración package.json:

Nota: Sourcemap debe estar activado; de lo contrario, se informará un error durante la ejecución: export GENERATE_SOURCEMAP=true. Agregue la variable de exportación al archivo de entorno .env.. La variable de entorno predeterminada del archivo .env.dev está activada GENERATE_SOURCEMAP=true.

{
    "scripts": {
    "dev": "craco start",
    "build": "craco build",
    "buildServe": "craco build && serve -s dist",
    "analyze": "export GENERATE_SOURCEMAP=true && yarn build && source-map-explorer dist/static/js/*.js"
  },
}

Código completo de craco.config.js:

const path = require('path')
const sassResourcesLoader = require('craco-sass-resources-loader')
const CompressionWebpackPlugin = require('compression-webpack-plugin')
const { getPlugin, pluginByName, whenProd } = require('@craco/craco')
const config = {
  devServer: {
    port: 8421,
  },
  webpack: {
    alias: {
      'geek-pc': path.resolve(__dirname, 'src'),
    },
    configure: (webpackConfig, { env, paths }) => {
      paths.appBuild = 'dist' // 修改打包输出文件目录
      webpackConfig.output = {
        ...webpackConfig.output,
        path: path.resolve(__dirname, 'dist'), // 修改打包输出文件目录 两步都要写
        publicPath: whenProd(() => '/', '/'), // 静态资源publicpath
      }
      // 线上替换cdn key:value key为库的名字 value为umd模块导出到global对象的key名
      whenProd(() => {
        webpackConfig.externals = {
          react: 'React',
          'react-dom': 'ReactDOM',
          history: 'History',
          'react-router-dom': 'ReactRouterDOM',
          redux: 'Redux',
          'react-redux': 'ReactRedux',
          dayjs: 'dayjs',
          antd: 'antd',
          axios: 'axios',
          '@ant-design/icons': 'icons',
        }
      })
      // 根据插件名获取插件 返回是否找到和匹配的插件
      const { isFound: isHtmlWebpackPluginFound, match: htmlWebpackPlugin } =
        getPlugin(webpackConfig, pluginByName('HtmlWebpackPlugin'))
      if (isHtmlWebpackPluginFound) {
        htmlWebpackPlugin.userOptions.title = whenProd(
          () => '生产环境',
          '开发环境'
        )
        // cdnurl要按照库的相互依赖优先级填写 被依赖的写前面优先加载
        htmlWebpackPlugin.userOptions.cdn = whenProd(
          () => ({
            js: [
              'https://cdn.bootcdn.net/ajax/libs/react/18.2.0/umd/react.production.min.js',
              'https://cdn.jsdelivr.net/npm/[email protected]/umd/react-router-dom.min.js',
              'https://cdnjs.cloudflare.com/ajax/libs/history/4.9.0/history.min.js',
              'https://cdn.bootcdn.net/ajax/libs/react-dom/18.2.0/umd/react-dom.production.min.js',
              'https://cdn.bootcdn.net/ajax/libs/redux/4.2.0/redux.min.js',
              'https://cdn.bootcdn.net/ajax/libs/react-redux/8.0.5/react-redux.min.js',
              'https://cdn.bootcdn.net/ajax/libs/dayjs/1.11.7/dayjs.min.js',
              'https://cdn.bootcdn.net/ajax/libs/antd/5.1.6/antd.min.js',
              'https://cdn.bootcdn.net/ajax/libs/axios/1.2.5/axios.min.js',
              'https://cdn.bootcdn.net/ajax/libs/ant-design-icons/5.0.1/index.umd.min.js',
            ],
            css: ['https://cdn.bootcdn.net/ajax/libs/antd/5.1.6/reset.min.css'],
          }),
          // 本地环境设为空 防止页面遍历报错
          {
            js: [],
            css: [],
          }
        )
      }
      // 使用gzip压缩超过1M的js和css文件
      webpackConfig.plugins.push(
        new CompressionWebpackPlugin({
          algorithm: 'gzip',
          test: /\.(js|css)$/,
          threshold: 1024,
          minRatio: 0.8,
        })
      )
      return webpackConfig
    },
  },
  plugins: [
    {
      plugin: sassResourcesLoader, // 在所有scss文件加载前加载 全局加载到前面
      options: {
        // 配置多个文件 传文件的绝对路径
        resources: [
          path.resolve(__dirname, 'src', 'styles', 'common.module.scss'),
          path.resolve(
            __dirname,
            'src',
            'styles',
            'global-variables.module.scss'
          ),
          path.resolve(__dirname, 'src', 'styles', 'antd.module.scss'),
        ],
      },
    },
  ],
}
module.exports = config

Adaptación de terminales móviles

hilo agregar postcss-px-to-viewport-8-plugin -D

const PostCssPxToViewportPlugin = require('postcss-px-to-viewport-8-plugin') // 针对postcss8.x版本生效的插件
module.exports = {
  style: {
    postcss: {
      mode: 'extends',
      loaderOptions: {
        postcssOptions: {
          ident: 'postcss',
          plugins: [
            'postcss-px-to-viewport-8-plugin',
            PostCssPxToViewportPlugin({
              viewportWidth: 375, // 视口宽度
              viewportUnit: 'vmin', // px转换后的单位
              fontViewportUnit: 'vmin', // 字体转换后的单位
            }),
          ],
        },
      },
    },
  },
}

Supongo que te gusta

Origin blog.csdn.net/Suk__/article/details/128880077
Recomendado
Clasificación