You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过正则配置eslint-plugin-simple-import-sort调整导入类型顺序?

问题描述

我正在使用eslint-plugin-simple-import-sort对导入语句排序,已在.eslintrc.json的overrides字段中为simple-import-sort/imports的groups定义了自定义规则。

当前同一模块组内的导入仅按包/路径名排序,效果如下:

import chatSystem from 'utils/chat-system';
import FirebaseUtils from 'utils/firebase';
import * as Imgix from 'utils/imgix';
import LinkHelper from 'utils/link-helper';
import { SOME_CONSTANT, someMethod } from 'utils/orders';

我希望调整为:默认导入在前,其次是* as类型导入,最后是解构式命名导入,期望效果:

import chatSystem from 'utils/chat-system';
import FirebaseUtils from 'utils/firebase';
import LinkHelper from 'utils/link-helper';
import * as Imgix from 'utils/imgix';
import { SOME_CONSTANT, someRandomMethod } from 'utils/orders';

请问能否通过正则规则实现该需求,无需编写自定义ESLint规则?

附当前.eslintrc.json相关配置片段:

{
  "extends": [
    "plugin:import/recommended"
  ],
  "plugins": ["simple-import-sort"],
  "rules": {
    "import/order": "off",
    "simple-import-sort/exports": "error",
    "simple-import-sort/imports": "error"
  },
  "overrides": [
    {
      "files": ["*.js"],
      "rules": {
        "simple-import-sort/imports": [
          "error",
          {
            "groups": [
              ["^react$", "react-redux", "^react-router", "redux", "^redux-"],
              ["^@", "^\\w"],
              ["^(actions)"],
              ["^(actions)(/.*)(types)"],
              ["^(reducers)(/.*|$)"],
              ["^(selectors)(/.*|$)"],
              ["^(components)(/.*|$)"],
              ["^(containers)(/.*|$)"],
              ["^(hooks)(/.*|$)"],
              ["^(constants)(/.*|$)"],
              ["^(utils)(/.*|$)"],
              ["^(config)(/.*|$)"],
              ["^\\.\\.(?!/?$)", "^\\.\\./?$"],
              ["^\\./(?=.*/)(?!/?$)", "^\\.(?!/?$)", "^\\./?$"],
              ["^.+\\.?(s?css)$"],
              ["^\\u0000"]
            ]
          }
        ]
      }
    }
  ]
}
解决方案

可以实现,无需自定义规则,有两种方案可选:

方案一:纯正则拆分组(适配JSON配置)

核心思路是:将每个自定义模块组(如utils、actions)拆成三个优先级连续的子组,顺序为「默认导入组 → 命名空间导入组 → 命名导入组」。利用插件“导入匹配到第一个符合的组后不再匹配后续组”的特性,让不同类型的导入进入对应优先级的组,从而实现排序。

修改后的overrides配置片段如下:

{
  "files": ["*.js"],
  "rules": {
    "simple-import-sort/imports": [
      "error",
      {
        "groups": [
          // 第三方库组
          ["^react$", "react-redux", "^react-router", "redux", "^redux-"],
          ["^@", "^\\w"],
          // 第一优先级:自定义模块的默认导入
          ["^(actions)"],
          ["^(actions)(/.*)(types)"],
          ["^(reducers)(/.*|$)"],
          ["^(selectors)(/.*|$)"],
          ["^(components)(/.*|$)"],
          ["^(containers)(/.*|$)"],
          ["^(hooks)(/.*|$)"],
          ["^(constants)(/.*|$)"],
          ["^(utils)(/.*|$)"],
          ["^(config)(/.*|$)"],
          // 第二优先级:自定义模块的命名空间(* as)导入
          ["^(actions)"],
          ["^(actions)(/.*)(types)"],
          ["^(reducers)(/.*|$)"],
          ["^(selectors)(/.*|$)"],
          ["^(components)(/.*|$)"],
          ["^(containers)(/.*|$)"],
          ["^(hooks)(/.*|$)"],
          ["^(constants)(/.*|$)"],
          ["^(utils)(/.*|$)"],
          ["^(config)(/.*|$)"],
          // 第三优先级:自定义模块的解构命名导入
          ["^(actions)"],
          ["^(actions)(/.*)(types)"],
          ["^(reducers)(/.*|$)"],
          ["^(selectors)(/.*|$)"],
          ["^(components)(/.*|$)"],
          ["^(containers)(/.*|$)"],
          ["^(hooks)(/.*|$)"],
          ["^(constants)(/.*|$)"],
          ["^(utils)(/.*|$)"],
          ["^(config)(/.*|$)"],
          // 相对路径组
          ["^\\.\\.(?!/?$)", "^\\.\\./?$"],
          ["^\\./(?=.*/)(?!/?$)", "^\\.(?!/?$)", "^\\./?$"],
          // 样式文件组
          ["^.+\\.?(s?css)$"],
          // 空导入组
          ["^\\u0000"]
        ]
      }
    ]
  }
}

说明

  • 插件按groups顺序匹配导入,默认导入会优先命中第一个对应的模块组,命名空间导入命中第二个,命名导入命中第三个。
  • 同一优先级组内的导入仍按模块路径的字母顺序排序,符合需求。

方案二:JS配置用函数排序(更简洁)

如果可以将.eslintrc.json改为.eslintrc.js,可以通过importType和sortImports函数直接在同一组内按导入类型排序,无需重复写模块组:

module.exports = {
  extends: ["plugin:import/recommended"],
  plugins: ["simple-import-sort"],
  rules: {
    "import/order": "off",
    "simple-import-sort/exports": "error",
    "simple-import-sort/imports": "error"
  },
  overrides: [
    {
      files: ["*.js"],
      rules: {
        "simple-import-sort/imports": [
          "error",
          {
            groups: [
              ["^react$", "react-redux", "^react-router", "redux", "^redux-"],
              ["^@", "^\\w"],
              ["^(actions)"],
              ["^(actions)(/.*)(types)"],
              ["^(reducers)(/.*|$)"],
              ["^(selectors)(/.*|$)"],
              ["^(components)(/.*|$)"],
              ["^(containers)(/.*|$)"],
              ["^(hooks)(/.*|$)"],
              ["^(constants)(/.*|$)"],
              ["^(utils)(/.*|$)"],
              ["^(config)(/.*|$)"],
              ["^\\.\\.(?!/?$)", "^\\.\\./?$"],
              ["^\\./(?=.*/)(?!/?$)", "^\\.(?!/?$)", "^\\./?$"],
              ["^.+\\.?(s?css)$"],
              ["^\\u0000"]
            ],
            importType: (importName) => {
              if (importName === null) return 'default'; // 默认导入
              if (importName === '*') return 'namespace'; // * as 导入
              return 'named'; // 解构命名导入
            },
            sortImports: (a, b) => {
              // 先按导入类型排序:default > namespace > named
              const typeOrder = { default: 0, namespace: 1, named: 2 };
              if (typeOrder[a.type] !== typeOrder[b.type]) {
                return typeOrder[a.type] - typeOrder[b.type];
              }
              // 类型相同则按模块路径排序
              return a.path.localeCompare(b.path);
            }
          }
        ]
      }
    }
  ]
};

说明

  • importType函数用于标记每个导入的类型。
  • sortImports函数定义排序逻辑:先按导入类型优先级排序,再按模块路径排序。

内容的提问来源于stack exchange,提问作者Lushmoney

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.16 21:50:21