JSDoc - 重用类型定义错误(找不到名称“类型名称”)

JSDoc - reusing type definitions error (cannot find name ‘type name’)

我有以下项目结构:

api/
  users/
    users.d.js

contexts/
  users/
    users.d.js

utils/
  users/
    users.d.js

utils/users/users.d.js 我正在定义可在整个系统中重用的类型。

例如下面的类型:

/**
 * Represents a User.
 *
 * @typedef {object} User
 * @property {string} id - Unique identifier.
 * …
 * @property {Date} birthday - Birthday.
 */

这很酷,现在我可以在我的模块 index.js 中重用它,如下所示:

import “./utils/users/users.d”;

/**
 * …
 * @param {User} user - The profile owner.
 */
function navigateToUserProfile(user) {
  …
}

而且效果很好!我的代码编辑器检测到类型并且可以毫无问题地自动生成文档:)

但是……如果 api/users/users.d.js 需要全局类型定义怎么办?

例如,如果在该模块中我有以下定义:

/**
 * @typedef {object} EditProfileInterface
 *
 * @property {User} newUserData - The new user data.
 * …
 */

为了重用全局定义,我需要在“本地类型定义”中导入实用程序模块(utils/users/users.d.js) ” 模块 (api/users/users.d.js).

好吧……那么,就这样吧:

// this code is inside api/users/users.d.js
import “../../utils/users/users.d”;

正如我们在里面所做的那样 index.js.

这是我的问题所在。这样做之后,JSDOC 将无法再正确生成文档。它将 api/users/users.d.js 的类型定义移动到文档的 全局部分

此外,如果我在导入 api/users/users.d.js 的模块中执行 // @ts-check,我会得到错误 找不到名称“EditProfileInterface”(未解析的类型)。这使得类型的可重用性变得非常困难……似乎没有比在模块之间复制定义更多的选择了 (?)

有什么建议或解决方法吗?我应该不关心在不同模块之间重复类型定义吗?

诀窍是配置 JSDoc 以支持 typescript 模式。

1- 创建一个 jsconfig.json 文件以便在整个项目中激活 ts-check:

这是我使用的代码:

{
  "compilerOptions": {
    "baseUrl": ".",
    "module": "commonjs",
    "target": "es2021",
    "jsx": "react-native",
    "checkJs": true, <--- ACTIVES the @ts-check directive in every single module of your project in order to avoid bugs :) 
  },
  "include": ["app/**/*.d.js", "app/**/*.js", "app/**/*.cjs", "app/**/*.mjs", "app/**/*.jsx"],
  "exclude": ["node_modules", "./functions/", "./docs"]
}

如果出现 linting 错误,只需 re-open VSCode。

2- 安装此开发依赖项:jsdoc-tsimport-plugin

yarn add --dev jsdoc-tsimport-plugin

3- 在您的 jsdoc 配置文件中,添加已安装的插件:

module.exports = {
  plugins: [
    "plugins/markdown",
    "node_modules/better-docs/category",
    "node_modules/jsdoc-tsimport-plugin/index.js", <------- THIS!
  ],
  source: {
    include: [
      "Main.jsx",
      "app/",
      "functions/",
      "shared/",
    ],
    includePattern: ".+\.(js(doc|x)?|(m|c)js)$",
    excludePattern: "(node_modules/|docs)",
  },
  sourceType: "module",
  tags: {
    allowUnknownTags: true,
    dictionaries: ["jsdoc", "closure"],
  },
  ...

4- 在您的 eslint 配置文件中,添加以下设置:

  extends: [
    "eslint:recommended",
    "airbnb",
    "prettier",
    "plugin:react/recommended",
    "plugin:react-native/all",
    "plugin:jsx-a11y/recommended",
    "plugin:react-hooks/recommended",
    "plugin:import/recommended",
    "plugin:flowtype/recommended",
    "plugin:jsdoc/recommended",
  ],
  settings: {
    jsdoc: {
      mode: "typescript", <--- THIS!
    },
  },
  rules: {
  ...

现在,您可以在 JSDOC 中使用 TYPESCRIPT 语法

例如,在这个项目结构中:

shared/
   types.d.js

api/
   users/
      users.d.js

您可以在全局类型中定义类型(在共享文件夹内):

/**
  * Some description for the type definition.
  *
  * @typedef SomeGlobalType
  * @property {string} [text="Hello world"] - Description for the property.
  */

然后,只需将其导入 api/users/users.d.js,如下所示:

 /**
  * @typedef User
  * @property {import("../../shared/types.d").SomeGlobalType} tricky - HEHE 
  */

就是这些 ;)