通过自定义UI组件库,样式jsx CSS不会应用在NextJs服务器端页面上

时间:2019-05-08 18:33:48

标签: javascript css webpack babeljs next.js

我们已经使用Styled-jsx创建了自定义的react ui组件库。而且我们在NextJs项目之一中将其作为依赖项使用。

在NextJs服务器上,我们不以某种方式无法从ui组件库中获取组件的样式,但是一旦将页面提供给客户端,我们就会获取所有已配置的样式。

  1. UI组件库的Webpack配置:-
const path = require('path');

module.exports = {
    entry: './src/index.js',
    module: {
        rules: [
            {
                test: /\.(js|jsx)$/,
                use: {
                    loader: 'babel-loader',
                },
            }
        ],
    },
    resolve: {
        extensions: ['.js', '.jsx'],
    },
    output: {
        path: path.resolve(__dirname, 'dist/'),
        publicPath: '',
        filename: 'index.js',
        libraryTarget: 'commonjs2'
    },
};
  1. UI组件库的Babel Config:-
{
    "env": {
        "development": {
            "presets": [
                ["@babel/preset-env"],
                "@babel/preset-react"
            ],
            "plugins": [
                ["styled-jsx/babel", { "optimizeForSpeed": true }],
                "@babel/plugin-proposal-class-properties"
            ]
        },
        "production": {
            "presets": [
                ["@babel/preset-env"],
                "@babel/preset-react"
            ],
            "plugins": [
                ["styled-jsx/babel", { "optimizeForSpeed": true }],
                "@babel/plugin-proposal-class-properties"
            ]
        },
        "test": {
            "presets": [
                "@babel/preset-react"
            ],
            "plugins": [
                "styled-jsx/babel-test",
                "@babel/plugin-proposal-class-properties"
            ]
        }
    }
}

  1. UI库使用者的NextJs配置
const path = require('path');

require('@babel/register')({
  presets: ['@babel/preset-env'],
});

const styledJsxLoader = require('styled-jsx/webpack');
const { localStaticPrefix } = require('./src/configs/urlConfigs/urlPrefix');

module.exports = {
  assetPrefix: localStaticPrefix,
  poweredByHeader: false,
  webpack(config, { dev, isServer, defaultLoaders }) {
    config.module.rules.push(
      {
        test: /\.(svg|ttf|eot)$/i,
        loader: 'file-loader?outputPath=static/',
      },
      {
        test: /\.+(js|jsx|ts|tsx)$/,
        loader: defaultLoaders.babel,
        include: [
          path.join(__dirname, 'node_modules/loan-calculator'),
          path.join(__dirname, 'node_modules/ui-theme'),
        ],
      },
    );
    if (!dev) {
      config.devtool = 'source-map';
      if (!isServer) {
        const originalEntries = config.entry();
        config.entry = () =>
          new Promise(resolve => {
            originalEntries.then(entries => {
              let totalPages = 0;
              const filteredEntries = {};
              Object.keys(entries).forEach(key => {
                if (
                  !key.endsWith('.test.js') &&
                  !key.endsWith('.spec.js') &&
                  !key.endsWith('.labels.js')
                ) {
                  filteredEntries[key] = entries[key];
                  if (key.match(/\/pages\//)) {
                    totalPages += 1;
                  }
                }
              });
              config.optimization.splitChunks.cacheGroups.commons.minChunks =
                totalPages > 2 ? totalPages * 0.5 : 2;
              resolve(filteredEntries);
            });
          });
      }
    }
    return config;
  },
};
  1. 使用者的Babel配置
{
  "env": {
    "development": {
      "presets": [
        ["next/babel"],
        [
          "@babel/preset-env",
          {
            "useBuiltIns": "usage",
            "include": ["es6.map", "es6.set", "es6.object.assign"],
            "forceAllTransforms": true
          }
        ]
      ],
      "plugins": ["@babel/plugin-proposal-class-properties"]
    },
    "production": {
      "presets": [
        ["next/babel"],
        [
          "@babel/preset-env",
          {
            "useBuiltIns": "usage",
            "include": ["es6.map", "es6.set", "es6.object.assign"],
            "forceAllTransforms": true
          }
        ]
      ],
      "plugins": ["@babel/plugin-proposal-class-properties"]
    },
    "test": {
      "presets": ["next/babel"],
      "plugins": ["styled-jsx/babel-test", "dynamic-import-node"]
    }
  }
}
  1. 我们如何使用UI组件库
import { Button} from 'ui-components-lib';

摘要:- 当我们在客户端上获取页面时,该组件正在渲染而没有css类(使用样式化jsx)。 login button without style applied

但是几秒钟后(取决于连接速度)样式将应用于该组件。 login button with style

0 个答案:

没有答案