chore: 初始化仓库

This commit is contained in:
Lydanne
2026-02-15 22:02:21 +08:00
commit 08d011d63f
381 changed files with 87202 additions and 0 deletions

View File

@@ -0,0 +1,286 @@
# 插件开发指南
本指南介绍如何开发自定义 Spaceflow Extension。
## 前置知识
- [NestJS](https://nestjs.com/) 基础Module、Injectable、依赖注入
- [nest-commander](https://docs.nestjs.com/recipes/nest-commander) CLI 命令定义
- TypeScript
## 快速开始
### 使用模板创建
```bash
spaceflow create my-extension
```
这会在当前目录下创建一个标准的 Extension 模板。
### 手动创建
```bash
mkdir spaceflow-plugin-hello
cd spaceflow-plugin-hello
pnpm init
pnpm add @spaceflow/core
pnpm add -D typescript @types/node
```
## 目录结构
```text
spaceflow-plugin-hello/
├── src/
│ ├── hello.command.ts # 命令定义
│ ├── hello.service.ts # 业务逻辑
│ ├── hello.module.ts # NestJS 模块
│ ├── locales/ # i18n 资源
│ │ ├── zh-cn/
│ │ │ └── hello.json
│ │ ├── en/
│ │ │ └── hello.json
│ │ └── index.ts
│ └── index.ts # Extension 入口
├── package.json
├── tsconfig.json
└── README.md
```
## Extension 入口
每个 Extension 必须实现 `SpaceflowExtension` 接口:
```typescript
// src/index.ts
import type {
SpaceflowExtension,
SpaceflowExtensionMetadata,
} from "@spaceflow/core";
import { HelloModule } from "./hello.module";
import { helloLocales } from "./locales";
export class HelloExtension implements SpaceflowExtension {
getMetadata(): SpaceflowExtensionMetadata {
return {
name: "hello",
commands: ["hello"],
configKey: "hello",
description: "示例 Extension",
locales: helloLocales,
};
}
getModule() {
return HelloModule;
}
}
export default HelloExtension;
```
## 命令定义
使用 `@Command` 装饰器定义 CLI 命令:
```typescript
// src/hello.command.ts
import { Command, CommandRunner, Option } from "@spaceflow/core";
import { t } from "@spaceflow/core";
import { HelloService } from "./hello.service";
interface HelloOptions {
readonly name?: string;
}
@Command({
name: "hello",
description: t("hello:description"),
})
export class HelloCommand extends CommandRunner {
constructor(private readonly helloService: HelloService) {
super();
}
async run(_params: string[], options: HelloOptions): Promise<void> {
const name = options.name ?? "World";
console.log(this.helloService.greet(name));
}
@Option({
flags: "-n, --name <name>",
description: t("hello:options.name"),
})
parseName(val: string): string {
return val;
}
}
```
## 业务逻辑
```typescript
// src/hello.service.ts
import { Injectable } from "@spaceflow/core";
@Injectable()
export class HelloService {
greet(name: string): string {
return `Hello, ${name}!`;
}
}
```
## NestJS 模块
```typescript
// src/hello.module.ts
import { Module } from "@spaceflow/core";
import { HelloCommand } from "./hello.command";
import { HelloService } from "./hello.service";
@Module({
providers: [HelloCommand, HelloService],
})
export class HelloModule {}
```
## 使用核心能力
Extension 可以导入 `@spaceflow/core` 提供的共享模块:
```typescript
import { Module } from "@spaceflow/core";
import { GitSdkModule } from "@spaceflow/core";
import { LlmProxyModule } from "@spaceflow/core";
@Module({
imports: [
GitSdkModule, // Git 命令封装
LlmProxyModule, // 多 LLM 代理
],
providers: [MyCommand, MyService],
})
export class MyModule {}
```
在 Service 中注入使用:
```typescript
import { Injectable } from "@spaceflow/core";
import { GitSdkService } from "@spaceflow/core";
@Injectable()
export class MyService {
constructor(private readonly gitSdk: GitSdkService) {}
async getDiff(): Promise<string> {
return this.gitSdk.diff("HEAD~1", "HEAD");
}
}
```
### 可用的核心模块
| 模块 | 说明 |
|------|------|
| `GitProviderModule` | Git 平台适配器GitHub / Gitea |
| `GitSdkModule` | Git 命令封装 |
| `LlmProxyModule` | 多 LLM 统一代理 |
| `FeishuSdkModule` | 飞书 API |
| `StorageModule` | 本地存储 |
| `ParallelModule` | 并行执行工具 |
## package.json 规范
```json
{
"name": "@spaceflow/plugin-hello",
"version": "1.0.0",
"description": "Spaceflow Hello Extension",
"main": "./dist/index.js",
"types": "./dist/index.d.ts",
"type": "module",
"exports": {
".": {
"import": "./dist/index.js",
"types": "./dist/index.d.ts"
}
},
"peerDependencies": {
"@spaceflow/core": "^0.17.0"
},
"spaceflow": {
"commands": ["hello"],
"configKey": "hello"
}
}
```
## i18n 支持
`locales/` 目录下管理翻译资源:
```typescript
// src/locales/index.ts
import zhCN from "./zh-cn/hello.json";
import en from "./en/hello.json";
import { addLocaleResources } from "@spaceflow/core";
export const helloLocales: Record<string, Record<string, string>> = {
"zh-CN": zhCN,
en,
};
// Side-effect: 立即注册资源
addLocaleResources("hello", helloLocales);
```
```json
// src/locales/zh-cn/hello.json
{
"description": "打招呼命令",
"options.name": "名字"
}
```
```json
// src/locales/en/hello.json
{
"description": "Say hello",
"options.name": "Name"
}
```
## 构建与发布
### 构建
```bash
spaceflow build
```
### 本地测试
`spaceflow.json` 中使用 `link:` 引用本地 Extension
```json
{
"dependencies": {
"@spaceflow/plugin-hello": "link:./path/to/plugin-hello"
}
}
```
### 发布到 npm
```bash
npm publish
```
用户安装:
```bash
spaceflow install @spaceflow/plugin-hello
```