tsdoc typedoc_深入研究TypeDoc的工作流程和可扩展性

本文探讨了TypeDoc的工作原理,包括关键组件如Application、Converter、ProjectReflection和Renderer,以及如何扩展TypeDoc以实现自定义功能。通过注册组件、监听事件和处理数据,可以创建插件来增强TypeDoc的功能,如多语言支持。文章还介绍了插件开发过程中的具体步骤和示例,展示了如何在转换和渲染过程中操作或检索数据。
摘要由CSDN通过智能技术生成

tsdoc typedoc

by Alexander Kamenov

亚历山大·卡梅诺夫(Alexander Kamenov)

深入研究TypeDoc的工作流程和可扩展性 (A deep dive into TypeDoc’s workflow and extensibility)

This topic aims to cover the basics on how you could extend the TypeDoc library functionality and what are the opportunities that it provides.

本主题旨在涵盖有关如何扩展TypeDoc库功能以及它提供的机会的基础知识。

For those of you who are not familiar with TypeDoc, this is a library which allows you to generate an API documentation based on your comments from your TypeScript source code.

对于那些不熟悉TypeDoc的人来说 ,这是一个库,可让您根据来自TypeScript源代码的注释来生成API文档。

By default there are two possible outputs:

默认情况下,有两个可能的输出:

  • Static website

    静态网站

  • JSON file.

    JSON文件。

If you want to find more about configuration and terms of use please refer to the README.

如果要查找有关配置和使用条款的更多信息,请参阅README

我遇到的问题 (The problem I have encountered)

The lack of documentation is a really common scenario, and this was the problem we faced. As most of you probably know, debugging and digging into any kind of software with exploratory purposes takes time. That’s why I decided to contribute and share the knowledge I’ve gained during the development of a plugin which provides users with the ability to localize their documentation into multiple languages.

缺乏文档是一个非常普遍的情况,这就是我们面临的问题。 你们大多数人可能都知道,出于探索性目的调试和挖掘任何类型的软件都需要时间。 这就是为什么我决定贡献并分享我在开发插件时获得的知识的知识,该插件使用户能够将其文档本地化为多种语言。

Good example here is the Japanese API documentation that Ignite UI for Angular library provides.

这里的一个很好的例子是Ignite UI for Angular库提供的日语API文档

So I’m going to give a rough explanation of how TypeDoc works and what was the approach that was taken during the development of that plugin.

因此,我将对TypeDoc的工作原理以及该插件的开发过程中采用的方法做一个粗略的解释。

I won’t go much into detail about how the library works. Instead I will try to expose only the most important aspects of the execution flow which, in my opinion, are the base of the “tree” from where you can start exploring and diverting into different “branches”.

我不会详细介绍该库的工作方式。 相反,我将尝试仅公开执行流程中最重要的方面,在我看来,这些方面是“树”的基础,您可以从中开始探索并转移到不同的“分支”中。

So without wasting more time, let’s move on to the essential part.

因此,在不浪费更多时间的情况下,让我们继续进行必要的部分。

Typedoc的工作方式。 (How typedoc works.)

您需要了解的几个组件/类: (Several components/classes you need to know about:)
  • Application:

    应用范围

    The default main application

    默认主应用

    class.

    上课

  • Options:

    选项

    Aggregates and contributes configuration declarations, declared by components or plugins. Parses

    聚集并贡献由组件或插件声明的配置声明。 解析

    option values from various sources (config file, command-line, args, etc.)

    来自各种来源(配置文件,命令行,args等)的选项

  • Converter:

    转换器

    Compiles source files using

    使用以下命令编译源文件

    TypeScript and converts compiler symbols to reflections.

    TypeScript并将编译器符号转换为反射。

  • ProjectReflection:

    项目反映

    A reflection that represents the

    代表

    root of the project.

    项目的 根源

    The project

    该项目

    reflection acts as a global index. You may receive all reflections and source files of the processed project through this reflection.

    反射充当全局索引。 通过此反射,您可能会收到已处理项目的所有反射和源文件。

  • Renderer:

    渲染器

    The

    renderer processes is a representation of ProjectReflection, using a BaseTheme instance and writes the emitted html documents to an output directory.

    渲染器进程使用BaseTheme实例表示ProjectReflection ,并将发出的html文档写入输出目录。

    Simply, the

    简单来说,

    renderer is used for generating the documentation output.

    渲染器用于生成文档输出。

  • EventDispatcher:

    EventDispatcher

    A class that provides a custom event channel.

    提供自定义事件通道的类。

    You may bind a callback to an event with ‘on’ or remove with ‘off’.

    您可以使用“ on”将回调绑定到事件,也可以使用“ off”将回调绑定到事件。

  • Logger:

    记录器

    The logger provides you with the ability to log without interruption any kind of errors or messages like success, warn, log, verbose, etc.

    记录器使您能够记录日志而不会中断任何类型的错误或消息,例如成功,警告,日志,详细信息等。

  • PluginHost:

    PluginHost

    Responsible for discovering and loading plugins.

    负责发现和加载插件。

Typedoc执行流程: (Typedoc Execution Flow:)

  • Application tries to load all TypeDoc plugins by searching for ‘typedocplugin’ keyword declared into your package.json file.

    应用程序尝试通过搜索在package.json文件中声明的'typedocplugin'关键字来加载所有TypeDoc插件。

  • Converter: Using TypeScript API in order to compile the referred project. If any compile errors are detected in the project, the convert process ends with the error that has been encountered.

    Converter 使用TypeScript API来编译引用的项目。 如果在项目中检测到任何编译错误,则转换过程将以遇到的错误结束。

    From the above diagram you can see that during the

    从上图可以看到

    Resolve Reflections process, which comes right after the compilation process, the EventDispatcher emits several events which are a good prerequisite for manipulating or retrieving data.

    在编译过程之后立即进行“ 解决反射”过程, EventDispatcher发出几个事件,这些事件是操纵或检索数据的良好先决条件。

    Once the conversion process ends we receive a

    转换过程结束后,我们会收到

    ProjectReflection object which represents the project itself with all files and their comments.

    ProjectReflection对象,代表所有文件及其注释的项目本身。

  • Options: Determines what would be the output of your documentation based on the options you have passed. There are two variants:

    选项 根据您通过的选项确定文档的输出 有两种变体:

    1.

    1。

    JSON file: Represents a stringified version of ProjectReflection object. This is what the Serialization does

    JSON文件 :表示ProjectReflection对象的字符串化版本。 这就是序列化的作用

    2.

    2。

    Static HTML website.

    静态HTML网站。

  • Renderer: At first the renderer needs to ensure that the Theme that corresponds to the output static website and the output directory, are set up correctly. If everything is fine, the renderer starts mapping the Reflections with the Templates from the Theme.

    渲染器 首先, 渲染器需要确保正确设置了与输出静态网站输出目录相对应的主题 。 如果一切正常,则渲染器将开始使用Theme中模板映射“ 反射 ”。

    Here the

    在这里

    RendererEvent emits two events BeginRenderer/EndRenderer suitable for manipulating the output data.

    RendererEvent发出两个事件BeginRenderer / EndRenderer,适用于处理输出数据。

  • Finish Rendering: This is where the process ends and the output of generated documentation is provided.

    完成渲染 :这是过程结束的地方,提供了生成的文档的输出。

After that rough explanation and visualization of the execution flow we are ready to move on and see how to actually proceed with the extensibility.

在对执行流程进行了粗略的解释和可视化之后,我们准备继续进行下去,看看如何实际进行可扩展性

扩展typedoc (Extending typedoc)

设置项目: (Set up the project:)

The very first step we need to take is setting up a node project with npm.

我们需要采取的第一步是使用npm设置一个节点项目

Declare that keyword typedocplugin into your package.json:

在您的package.json中声明关键字typedocplugin

Then we need to export a module which would serve as an entry point of the project. How does TypeDoc load the plugins? It simply searches through all node_modules packages and their package.json file, and when that keyword is encountered it requires that package and executes it as a function by passing a reference to the main Application class.

然后,我们需要导出一个模块该模块将用作项目的入口点。 TypeDoc如何加载插件? 它仅搜索所有的node_modules软件包及其package.json文件,当遇到该关键字时,它需要该软件包并通过将引用传递给主Application类来将其作为函数执行。

Once all those steps are performed we have the freedom to manipulate the execution process and the output data as we want ?.

一旦完成所有这些步骤,我们就可以自由地根据需要操纵执行过程和输出数据

方法和例子 (Approaches and examples)

As I mentioned earlier, all the knowledge I share in this article was gained during the development of a localization plugin, which I firmly believe takes full advantage of what TypeDoc offers as an opportunity to extend. So all the examples and approaches below are inspired by the idea and the source of that “creature”.

正如我之前提到的,我在本文中分享的所有知识都是在开发本地化插件时获得的 ,我坚信,可以充分利用TypeDoc提供的功能作为扩展机会。 因此,以下所有示例和方法均受该“ 生物 ”的思想和来源的启发。

In order to understand how it works, you can go through the README file. It is enough to understand the first 3 steps.

为了了解它是如何工作的,您可以浏览自述文件。 了解前3个步骤就足够了。

Let’s start with the main module (index.ts) file which typedoc executes once it requires the plugin. As we already know, a reference to the default Application class is passed through the require callback, where you have access to all those main components we have talked about in the How TypeDoc works section.

让我们从主模块( index.ts )文件开始 需要插件时执行哪种typedoc 众所周知,对默认Application类的引用是通过require回调传递的,您可以在其中访问我们在TypeDoc的工作原理部分中讨论的所有主要组件。

Through all those component references you are able to register your own custom components, and depending on what they extend, a different set of events are provided.

通过所有这些组件引用,您可以注册自己的自定义组件,并根据它们扩展的内容提供不同的事件集。

Sometimes just a theory is insufficient, so let’s move on and see how things happen in practice.

有时仅凭一种理论是不够的,所以让我们继续前进,看看实际情况是如何发生的。

Here are the four most important things that we are going to review:

这是我们要回顾的四个最重要的事情:

  • Register our own options.

    注册我们自己的选项。

  • Manipulating or retrieving the data during the conversion process.

    在转换过程中处理或检索数据。

  • Manipulating or retrieving the data during the renderer process.

    渲染器过程中处理或检索数据。

注册我们自己的选项。 (Register our own option.)

As we already know, all of the component registrations happen in the main module. The important part here is that, in order to register a component within the options context, you need to extend the OptionsComponent class.

众所周知,所有组件注册都在main模块中进行 。 这里的重要部分是,为了在options上下文中注册组件,您需要扩展 OptionsComponent类。

The custom definition of the OptionComponent looks like this:

OptionComponent的自定义定义 看起来像这样:

At the end you need to add that declaration into the options that the application provides.

最后,您需要将该声明添加到应用程序提供的选项中。

You can refer to the README of the extension/plugin we are talking about and see what kind of options are exposed and how they contribute to the process.

您可以参考我们正在讨论的扩展程序/插件的自述文件 ,并了解公开了哪些选项以及它们如何对过程做出贡献。

在转换过程中处理或检索数据 (Manipulating or retrieving the data during the conversion process)

The registration process here is the same, but instead of extending OptionsComponent you need to extend ConverterComponent.

这里的注册过程是相同的,但是除了扩展OptionsComponent之外,您还需要扩展ConverterComponent

As you probably understood, the way we interact with the data is through the events that the EventDispatcher emits. So all the events that you can subscribe for within that context can be found and accessed through the Converter.

如您所知,我们与数据交互的方式是通过EventDispatcher 发出事件 。 因此,可以在Converter中找到和访问您可以在该上下文中预订的所有事件

We will take a look within the context of the EVENT_RESOLVE event callback. The event gets triggered every time when TypeDoc resolves a Class, Interface or Enum or (method, property, etc.) part of a particular Class, Interface or Enum. Wait what?

我们将在EVENT_RESOLVE 事件回调的上下文中进行查看。 每当TypeDoc解析接口枚举或特定接口枚举的 ( 方法属性 )部分时,都会触发该事件。 等等什么

Okay It’s a bit of confusing, but the concept is as simple as iterating an array.

好的,这有点令人困惑,但是这个概念就像迭代数组一样简单。

Let’s take an example of a simple class.

让我们以一个简单的类为例。

The event will emit four times referencing each unit per this declaration, transformed in DeclarationReflection:

根据该声明,该事件将发出四次引用每个单元的信息,并在DeclarationReflection中进行转换:

  1. Emits the class with reference to all his children (b, c, d).

    参考他所有的孩子 ( bc,d ) 退出 课堂。

  2. Emits the property b with reference to his parent (class A).

    参照其父项 (类A ) 发出 属性b

  3. Emits the property c with reference to his parent (class A).

    参照其父项 放弃 属性c ( A类)。

  4. Emits the method d with reference to his parent (class A).

    参考其父项 发出 方法d ( A类)。

Hope everything is clearer now!

希望现在一切都变清楚了!

Let’s see how we can subscribe for the emitted events:

让我们看看如何订阅发出的事件:

Then in the resolve callback you can see how the comments per every Class, Enum and Interface are taken and stored into a JSON file which represents each unit (Class, Enum, Interface) separately. For instance if we have two classes A and B, the output folder would contain two JSON files A.json and B.json.

然后在resolve回调中,您可以看到如何将每个ClassEnumInterface的注释提取并存储到一个JSON文件中,该JSON文件分别表示每个单元( ClassEnumInterface )。 例如,如果我们有两个类AB,则输出文件夹将包含两个JSON文件A.jsonB.json

The next example represents the moment where the comments per every getter and setter are retrieved which is the next unit of the Class declaration we talked about a little earlier.

下一个示例表示检索每个gettersetter的注释的时刻,这是我们稍早谈到的Class声明的下一个单元。

These are just examples, of course — you can do whatever you want here.

当然,这些仅仅是示例-您可以在这里做任何您想做的事情。

在“渲染器”过程中处理或检索数据 (Manipulating or retrieving the data during the Renderer process)

Here we have the same concept as the Convert, but of course we need to extend another class. Guess what — the name of the class is RendererComponent, and the object that holds the event references is RendererEvent.

在这里,我们具有与Convert相同的概念,但是我们当然需要扩展另一个类。 猜猜是什么-类的名称是RendererComponent ,保存事件引用的对象是RendererEvent

The variety of the events is less than the Converter but the information that the events provide is more than enough.

事件的种类少于转换器 但是事件提供的信息绰绰有余。

Subscription is the same:

订阅相同:

Here, the behavior of the RendererEvent.BEGIN event is a bit different. It gets triggered just once when the Renderer process has just started. Then all of the reflections that the Converter has created are taken, and with the “power” of the forEach we are going through each DeclarationReflection and processing it:

在这里, RendererEvent.BEGIN事件的行为有些不同。 渲染器进程刚刚开始时,它仅触发一次。 然后,将获取Converter创建的所有反射 ,并使用forEach的“ 力量 ”来遍历每个DeclarationReflection并对其进行处理:

What does the process do? It just takes the location of the JSON files that the Converter has built and replaces the content from those JSONs with the content in the reflection.

这个过程是做什么的? 它只是需要的JSON文件的位置,该转换器已建成并取代那些JSONs与反射的内容的内容。

The example here again refers the manipulation of the getters and setters per current Class:

这里的示例再次引用了对每个当前Classgettersetter的操作:

Of course again here you can improvise and do whatever you need.

当然,您可以在这里再次即兴创作并做您需要的任何事情。

结论 (Conclusion)

This is probably only one third of what the plugin does. There is much more that I can show and expose as functionality. For example how we came up with a solution for manipulating the hardcoded strings within our custom theme. But the purpose of this blog is focused on the extensibility and manipulation of the data. So if you have further questions or interests you can let me know in the comments below.

这可能只是插件功能的三分之一。 我可以展示和展示更多功能。 例如,我们如何提出在自定义主题中处理硬编码字符串的解决方案。 但是,此博客的目的是针对数据可扩展性操作性 。 因此,如果您还有其他问题或兴趣,可以在下面的评论中告诉我。

翻译自: https://www.freecodecamp.org/news/a-deep-dive-into-typedocs-workflow-and-extensibility-d464683e092c/

tsdoc typedoc

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值