跳转至

Service:插件中的长期服务对象

Service 用来封装可复用的插件逻辑。平台会按需创建服务实例,并保证对应作用域内只有一个实例。

服务类型

类型 作用域 适合场景
Application Service 整个 IDE 进程 全局配置、跨项目缓存、全局客户端
Project Service 单个项目 项目级状态、项目级索引协调、项目配置
Module Service 单个模块 很少使用;大型项目中容易增加内存压力

一般优先使用 Application Service 或 Project Service。

Light Service

如果服务不需要被其他插件覆盖,也不作为公开 API,优先使用 @Service 注解。

import com.intellij.openapi.components.Service

@Service(Service.Level.PROJECT)
class MyProjectService {
    fun doWork() {
        // project-level logic
    }
}

获取服务:

val service = project.getService(MyProjectService::class.java)

Application 级服务:

@Service
class MyAppService {
    fun doWork() {
        // application-level logic
    }
}
val service = com.intellij.openapi.application.ApplicationManager
    .getApplication()
    .getService(MyAppService::class.java)

构造函数规则

服务构造函数应尽量轻量:

  • 不要在构造函数里做耗时初始化。
  • 不要在构造函数里主动获取一堆其他服务。
  • Project Service 可以接收 Project
  • Kotlin 协程场景可以接收平台提供的 CoroutineScope

示例:

@Service(Service.Level.PROJECT)
class MyProjectService(
    private val project: com.intellij.openapi.project.Project
) {
    fun projectName(): String = project.name
}

非 Light Service 注册

如果服务需要接口、测试实现、Headless 实现或希望暴露给其他插件,可以在 plugin.xml 中声明:

<extensions defaultExtensionNs="com.intellij">
  <projectService
      serviceInterface="com.example.MyProjectService"
      serviceImplementation="com.example.MyProjectServiceImpl"/>
</extensions>

生命周期与清理

需要释放资源时实现 Disposable

class MyService : com.intellij.openapi.Disposable {
    override fun dispose() {
        // close resources
    }
}

不要自己猜测 IDE 关闭时机。把资源挂到平台生命周期上,让平台负责调用清理逻辑。

参考来源