openclaw-rocketchat 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (85) hide show
  1. package/LICENSE +21 -0
  2. package/README.en.md +694 -0
  3. package/README.md +730 -0
  4. package/dist/cli/add-bot.d.ts +2 -0
  5. package/dist/cli/add-bot.d.ts.map +1 -0
  6. package/dist/cli/add-bot.js +138 -0
  7. package/dist/cli/add-bot.js.map +1 -0
  8. package/dist/cli/add-group.d.ts +2 -0
  9. package/dist/cli/add-group.d.ts.map +1 -0
  10. package/dist/cli/add-group.js +145 -0
  11. package/dist/cli/add-group.js.map +1 -0
  12. package/dist/cli/add-user.d.ts +2 -0
  13. package/dist/cli/add-user.d.ts.map +1 -0
  14. package/dist/cli/add-user.js +186 -0
  15. package/dist/cli/add-user.js.map +1 -0
  16. package/dist/cli/invite.d.ts +2 -0
  17. package/dist/cli/invite.d.ts.map +1 -0
  18. package/dist/cli/invite.js +194 -0
  19. package/dist/cli/invite.js.map +1 -0
  20. package/dist/cli/prompts.d.ts +24 -0
  21. package/dist/cli/prompts.d.ts.map +1 -0
  22. package/dist/cli/prompts.js +134 -0
  23. package/dist/cli/prompts.js.map +1 -0
  24. package/dist/cli/remove-user.d.ts +2 -0
  25. package/dist/cli/remove-user.d.ts.map +1 -0
  26. package/dist/cli/remove-user.js +108 -0
  27. package/dist/cli/remove-user.js.map +1 -0
  28. package/dist/cli/setup.d.ts +2 -0
  29. package/dist/cli/setup.d.ts.map +1 -0
  30. package/dist/cli/setup.js +446 -0
  31. package/dist/cli/setup.js.map +1 -0
  32. package/dist/cli/status.d.ts +2 -0
  33. package/dist/cli/status.d.ts.map +1 -0
  34. package/dist/cli/status.js +161 -0
  35. package/dist/cli/status.js.map +1 -0
  36. package/dist/cli/uninstall.d.ts +2 -0
  37. package/dist/cli/uninstall.d.ts.map +1 -0
  38. package/dist/cli/uninstall.js +81 -0
  39. package/dist/cli/uninstall.js.map +1 -0
  40. package/dist/config/credentials.d.ts +26 -0
  41. package/dist/config/credentials.d.ts.map +1 -0
  42. package/dist/config/credentials.js +169 -0
  43. package/dist/config/credentials.js.map +1 -0
  44. package/dist/config/writer.d.ts +52 -0
  45. package/dist/config/writer.d.ts.map +1 -0
  46. package/dist/config/writer.js +170 -0
  47. package/dist/config/writer.js.map +1 -0
  48. package/dist/docker/compose.d.ts +10 -0
  49. package/dist/docker/compose.d.ts.map +1 -0
  50. package/dist/docker/compose.js +56 -0
  51. package/dist/docker/compose.js.map +1 -0
  52. package/dist/docker/manager.d.ts +38 -0
  53. package/dist/docker/manager.d.ts.map +1 -0
  54. package/dist/docker/manager.js +219 -0
  55. package/dist/docker/manager.js.map +1 -0
  56. package/dist/index.d.ts +5 -0
  57. package/dist/index.d.ts.map +1 -0
  58. package/dist/index.js +203 -0
  59. package/dist/index.js.map +1 -0
  60. package/dist/rc-api/rest-client.d.ts +64 -0
  61. package/dist/rc-api/rest-client.d.ts.map +1 -0
  62. package/dist/rc-api/rest-client.js +268 -0
  63. package/dist/rc-api/rest-client.js.map +1 -0
  64. package/dist/rc-api/types.d.ts +158 -0
  65. package/dist/rc-api/types.d.ts.map +1 -0
  66. package/dist/rc-api/types.js +5 -0
  67. package/dist/rc-api/types.js.map +1 -0
  68. package/dist/rc-api/ws-client.d.ts +47 -0
  69. package/dist/rc-api/ws-client.d.ts.map +1 -0
  70. package/dist/rc-api/ws-client.js +308 -0
  71. package/dist/rc-api/ws-client.js.map +1 -0
  72. package/dist/service/bot-manager.d.ts +34 -0
  73. package/dist/service/bot-manager.d.ts.map +1 -0
  74. package/dist/service/bot-manager.js +156 -0
  75. package/dist/service/bot-manager.js.map +1 -0
  76. package/dist/service/channel.d.ts +35 -0
  77. package/dist/service/channel.d.ts.map +1 -0
  78. package/dist/service/channel.js +157 -0
  79. package/dist/service/channel.js.map +1 -0
  80. package/dist/service/message-handler.d.ts +45 -0
  81. package/dist/service/message-handler.d.ts.map +1 -0
  82. package/dist/service/message-handler.js +207 -0
  83. package/dist/service/message-handler.js.map +1 -0
  84. package/openclaw.plugin.json +45 -0
  85. package/package.json +61 -0
@@ -0,0 +1,81 @@
1
+ // ============================================================
2
+ // CLI: openclaw rocketchat uninstall
3
+ // 卸载 Rocket.Chat(停止容器、清理配置)
4
+ // ============================================================
5
+ import { rm } from "node:fs/promises";
6
+ import { DockerManager } from "../docker/manager.js";
7
+ import { ConfigWriter } from "../config/writer.js";
8
+ import { getDockerDir, loadAdminCredentials, } from "../config/credentials.js";
9
+ import { confirm, heading, step, success, error, info, warn, } from "./prompts.js";
10
+ import { homedir } from "node:os";
11
+ import { join } from "node:path";
12
+ export async function uninstallCommand(configPath) {
13
+ heading("卸载 Rocket.Chat");
14
+ const adminCreds = await loadAdminCredentials();
15
+ if (!adminCreds) {
16
+ warn("未检测到 Rocket.Chat 安装。");
17
+ return;
18
+ }
19
+ warn("这将停止并移除 Rocket.Chat 容器!");
20
+ console.log("");
21
+ const proceed = await confirm("确定要卸载?");
22
+ if (!proceed) {
23
+ info("已取消。");
24
+ return;
25
+ }
26
+ const deleteData = await confirm("是否删除所有数据(聊天记录)?");
27
+ // ----------------------------------------------------------
28
+ // 1. 停止并移除容器
29
+ // ----------------------------------------------------------
30
+ console.log("");
31
+ const dockerDir = getDockerDir();
32
+ const docker = new DockerManager(dockerDir);
33
+ if (docker.composeFileExists()) {
34
+ step("停止容器...");
35
+ try {
36
+ await docker.remove(deleteData);
37
+ success("容器已移除");
38
+ }
39
+ catch (err) {
40
+ error(`容器移除失败: ${err.message}`);
41
+ info("请手动运行: docker compose down");
42
+ }
43
+ }
44
+ // ----------------------------------------------------------
45
+ // 2. 清理配置
46
+ // ----------------------------------------------------------
47
+ step("清理 openclaw.json 中的 rocketchat 配置...");
48
+ try {
49
+ const configWriter = new ConfigWriter(configPath);
50
+ await configWriter.readConfig();
51
+ configWriter.removeRocketchatConfig();
52
+ await configWriter.save();
53
+ success("配置已清理");
54
+ }
55
+ catch (err) {
56
+ error(`配置清理失败: ${err.message}`);
57
+ }
58
+ // ----------------------------------------------------------
59
+ // 3. 清理凭据文件
60
+ // ----------------------------------------------------------
61
+ step("清理凭据文件...");
62
+ try {
63
+ const credDir = join(homedir(), ".openclaw", "credentials", "rocketchat");
64
+ await rm(credDir, { recursive: true, force: true });
65
+ success("凭据文件已清理");
66
+ }
67
+ catch {
68
+ // 不影响
69
+ }
70
+ // ----------------------------------------------------------
71
+ // 完成
72
+ // ----------------------------------------------------------
73
+ console.log("");
74
+ success("Rocket.Chat 已卸载");
75
+ if (!deleteData) {
76
+ info(" 数据卷已保留,彻底清除请运行:");
77
+ info(" docker volume rm openclaw-rc_mongodb_data");
78
+ }
79
+ console.log("");
80
+ }
81
+ //# sourceMappingURL=uninstall.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"uninstall.js","sourceRoot":"","sources":["../../src/cli/uninstall.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,26 @@
1
+ import type { AdminCredentials, BotCredentials, UserRecord } from "../rc-api/types.js";
2
+ /** Docker compose 文件存储目录 */
3
+ export declare function getDockerDir(): string;
4
+ /** 保存管理员凭据 */
5
+ export declare function saveAdminCredentials(creds: AdminCredentials): Promise<void>;
6
+ /** 读取管理员凭据 */
7
+ export declare function loadAdminCredentials(): Promise<AdminCredentials | null>;
8
+ /** 保存机器人凭据 */
9
+ export declare function saveBotCredentials(botUsername: string, userId: string, password: string): Promise<void>;
10
+ /** 读取所有机器人凭据 */
11
+ export declare function loadBotCredentials(): Promise<BotCredentials>;
12
+ /** 移除机器人凭据 */
13
+ export declare function removeBotCredential(botUsername: string): Promise<void>;
14
+ /** 保存用户记录 */
15
+ export declare function saveUserRecord(username: string, permission?: "full" | "readonly"): Promise<void>;
16
+ /** 读取用户记录 */
17
+ export declare function loadUserRecords(): Promise<UserRecord[]>;
18
+ /** 移除用户记录 */
19
+ export declare function removeUserRecord(username: string): Promise<void>;
20
+ /** 生成随机密码 */
21
+ export declare function generatePassword(length?: number): string;
22
+ /** 生成随机管理员用户名 */
23
+ export declare function generateAdminUsername(): string;
24
+ /** 检查凭据是否存在(是否已经 setup 过) */
25
+ export declare function isSetupDone(): boolean;
26
+ //# sourceMappingURL=credentials.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"credentials.d.ts","sourceRoot":"","sources":["../../src/config/credentials.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAAE,gBAAgB,EAAE,cAAc,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAOvF,4BAA4B;AAC5B,wBAAgB,YAAY,IAAI,MAAM,CAErC;AAsBD,cAAc;AACd,wBAAsB,oBAAoB,CACxC,KAAK,EAAE,gBAAgB,GACtB,OAAO,CAAC,IAAI,CAAC,CAOf;AAED,cAAc;AACd,wBAAsB,oBAAoB,IAAI,OAAO,CAAC,gBAAgB,GAAG,IAAI,CAAC,CAU7E;AAMD,cAAc;AACd,wBAAsB,kBAAkB,CACtC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,MAAM,GACf,OAAO,CAAC,IAAI,CAAC,CAgBf;AAED,gBAAgB;AAChB,wBAAsB,kBAAkB,IAAI,OAAO,CAAC,cAAc,CAAC,CASlE;AAED,cAAc;AACd,wBAAsB,mBAAmB,CACvC,WAAW,EAAE,MAAM,GAClB,OAAO,CAAC,IAAI,CAAC,CAUf;AAMD,aAAa;AACb,wBAAsB,cAAc,CAClC,QAAQ,EAAE,MAAM,EAChB,UAAU,GAAE,MAAM,GAAG,UAAmB,GACvC,OAAO,CAAC,IAAI,CAAC,CAqBf;AAED,aAAa;AACb,wBAAsB,eAAe,IAAI,OAAO,CAAC,UAAU,EAAE,CAAC,CAQ7D;AAED,aAAa;AACb,wBAAsB,gBAAgB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAUtE;AAMD,aAAa;AACb,wBAAgB,gBAAgB,CAAC,MAAM,SAAK,GAAG,MAAM,CAEpD;AAED,iBAAiB;AACjB,wBAAgB,qBAAqB,IAAI,MAAM,CAE9C;AAED,6BAA6B;AAC7B,wBAAgB,WAAW,IAAI,OAAO,CAErC"}
@@ -0,0 +1,169 @@
1
+ // ============================================================
2
+ // 凭据存储管理
3
+ // 敏感信息存储在 ~/.openclaw/credentials/rocketchat/
4
+ // ============================================================
5
+ import { readFile, writeFile, mkdir, chmod } from "node:fs/promises";
6
+ import { existsSync } from "node:fs";
7
+ import { join } from "node:path";
8
+ import { homedir, platform } from "node:os";
9
+ import { randomBytes } from "node:crypto";
10
+ /** 凭据存储根目录 */
11
+ function getCredentialsDir() {
12
+ return join(homedir(), ".openclaw", "credentials", "rocketchat");
13
+ }
14
+ /** Docker compose 文件存储目录 */
15
+ export function getDockerDir() {
16
+ return join(getCredentialsDir(), "docker");
17
+ }
18
+ /** 确保目录存在,macOS/Linux 上设置 0o700 权限 */
19
+ async function ensureDir(dir) {
20
+ await mkdir(dir, { recursive: true, mode: 0o700 });
21
+ }
22
+ /**
23
+ * 写入敏感文件
24
+ * macOS/Linux 上自动设置 0o600 权限(仅文件所有者可读写)
25
+ */
26
+ async function writeSecureFile(filePath, content) {
27
+ await writeFile(filePath, content, "utf-8");
28
+ if (platform() !== "win32") {
29
+ await chmod(filePath, 0o600);
30
+ }
31
+ }
32
+ // ----------------------------------------------------------
33
+ // 管理员凭据
34
+ // ----------------------------------------------------------
35
+ /** 保存管理员凭据 */
36
+ export async function saveAdminCredentials(creds) {
37
+ const dir = getCredentialsDir();
38
+ await ensureDir(dir);
39
+ await writeSecureFile(join(dir, "admin.json"), JSON.stringify(creds, null, 2));
40
+ }
41
+ /** 读取管理员凭据 */
42
+ export async function loadAdminCredentials() {
43
+ const file = join(getCredentialsDir(), "admin.json");
44
+ if (!existsSync(file))
45
+ return null;
46
+ try {
47
+ const content = await readFile(file, "utf-8");
48
+ return JSON.parse(content);
49
+ }
50
+ catch (err) {
51
+ console.error(`[rocketchat] 读取管理员凭据失败: ${err.message}`);
52
+ return null;
53
+ }
54
+ }
55
+ // ----------------------------------------------------------
56
+ // 机器人凭据
57
+ // ----------------------------------------------------------
58
+ /** 保存机器人凭据 */
59
+ export async function saveBotCredentials(botUsername, userId, password) {
60
+ const dir = getCredentialsDir();
61
+ await ensureDir(dir);
62
+ const file = join(dir, "bots.json");
63
+ let bots = {};
64
+ if (existsSync(file)) {
65
+ try {
66
+ bots = JSON.parse(await readFile(file, "utf-8"));
67
+ }
68
+ catch {
69
+ bots = {};
70
+ }
71
+ }
72
+ bots[botUsername] = { userId, password };
73
+ await writeSecureFile(file, JSON.stringify(bots, null, 2));
74
+ }
75
+ /** 读取所有机器人凭据 */
76
+ export async function loadBotCredentials() {
77
+ const file = join(getCredentialsDir(), "bots.json");
78
+ if (!existsSync(file))
79
+ return {};
80
+ try {
81
+ return JSON.parse(await readFile(file, "utf-8"));
82
+ }
83
+ catch (err) {
84
+ console.error(`[rocketchat] 读取机器人凭据失败: ${err.message}`);
85
+ return {};
86
+ }
87
+ }
88
+ /** 移除机器人凭据 */
89
+ export async function removeBotCredential(botUsername) {
90
+ const file = join(getCredentialsDir(), "bots.json");
91
+ if (!existsSync(file))
92
+ return;
93
+ try {
94
+ const bots = JSON.parse(await readFile(file, "utf-8"));
95
+ delete bots[botUsername];
96
+ await writeSecureFile(file, JSON.stringify(bots, null, 2));
97
+ }
98
+ catch {
99
+ // 忽略
100
+ }
101
+ }
102
+ // ----------------------------------------------------------
103
+ // 用户记录
104
+ // ----------------------------------------------------------
105
+ /** 保存用户记录 */
106
+ export async function saveUserRecord(username, permission = "full") {
107
+ const dir = getCredentialsDir();
108
+ await ensureDir(dir);
109
+ const file = join(dir, "users.json");
110
+ let users = [];
111
+ if (existsSync(file)) {
112
+ try {
113
+ users = JSON.parse(await readFile(file, "utf-8"));
114
+ }
115
+ catch {
116
+ users = [];
117
+ }
118
+ }
119
+ const existing = users.find((u) => u.username === username);
120
+ if (existing) {
121
+ existing.permission = permission;
122
+ }
123
+ else {
124
+ users.push({ username, createdAt: new Date().toISOString(), permission });
125
+ }
126
+ await writeSecureFile(file, JSON.stringify(users, null, 2));
127
+ }
128
+ /** 读取用户记录 */
129
+ export async function loadUserRecords() {
130
+ const file = join(getCredentialsDir(), "users.json");
131
+ if (!existsSync(file))
132
+ return [];
133
+ try {
134
+ return JSON.parse(await readFile(file, "utf-8"));
135
+ }
136
+ catch {
137
+ return [];
138
+ }
139
+ }
140
+ /** 移除用户记录 */
141
+ export async function removeUserRecord(username) {
142
+ const file = join(getCredentialsDir(), "users.json");
143
+ if (!existsSync(file))
144
+ return;
145
+ try {
146
+ let users = JSON.parse(await readFile(file, "utf-8"));
147
+ users = users.filter((u) => u.username !== username);
148
+ await writeSecureFile(file, JSON.stringify(users, null, 2));
149
+ }
150
+ catch {
151
+ // 文件损坏时忽略
152
+ }
153
+ }
154
+ // ----------------------------------------------------------
155
+ // 工具
156
+ // ----------------------------------------------------------
157
+ /** 生成随机密码 */
158
+ export function generatePassword(length = 24) {
159
+ return randomBytes(length).toString("base64url").slice(0, length);
160
+ }
161
+ /** 生成随机管理员用户名 */
162
+ export function generateAdminUsername() {
163
+ return `rc-admin-${randomBytes(4).toString("hex")}`;
164
+ }
165
+ /** 检查凭据是否存在(是否已经 setup 过) */
166
+ export function isSetupDone() {
167
+ return existsSync(join(getCredentialsDir(), "admin.json"));
168
+ }
169
+ //# sourceMappingURL=credentials.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"credentials.js","sourceRoot":"","sources":["../../src/config/credentials.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,52 @@
1
+ import type { RocketchatChannelConfig, OpenClawAgent, OpenClawBinding } from "../rc-api/types.js";
2
+ /** openclaw.json 的根结构(部分) */
3
+ interface OpenClawConfig {
4
+ agents?: {
5
+ list?: OpenClawAgent[];
6
+ };
7
+ bindings?: OpenClawBinding[];
8
+ channels?: {
9
+ rocketchat?: Partial<RocketchatChannelConfig>;
10
+ [key: string]: unknown;
11
+ };
12
+ [key: string]: unknown;
13
+ }
14
+ export declare class ConfigWriter {
15
+ private configPath;
16
+ private config;
17
+ constructor(configPath: string);
18
+ /** 读取 openclaw.json */
19
+ readConfig(): Promise<OpenClawConfig>;
20
+ /** 获取已有 Agent 列表(只读) */
21
+ getAgentsList(): OpenClawAgent[];
22
+ /** 获取 Rocket.Chat 频道配置 */
23
+ getRocketchatConfig(): Partial<RocketchatChannelConfig> | undefined;
24
+ /** 获取所有 rocketchat 相关的 bindings */
25
+ getRocketchatBindings(): OpenClawBinding[];
26
+ /** 获取所有 bindings */
27
+ getAllBindings(): OpenClawBinding[];
28
+ /** 设置基础配置(setup 命令调用) */
29
+ setRocketchatChannel(serverUrl: string, port: number): void;
30
+ /** 添加机器人账号(add-bot 命令调用) */
31
+ addBotAccount(accountId: string, botUsername: string, displayName?: string): void;
32
+ /** 添加 binding(add-bot 命令调用) */
33
+ addBinding(agentId: string, accountId: string): void;
34
+ /** 添加群组(add-group 命令调用) */
35
+ addGroup(name: string, bots: string[], requireMention: boolean): void;
36
+ /** 移除机器人账号 */
37
+ removeBotAccount(accountId: string): void;
38
+ /** 移除群组 */
39
+ removeGroup(name: string): void;
40
+ /** 清除所有 rocketchat 相关配置 */
41
+ removeRocketchatConfig(): void;
42
+ /** 保存到文件
43
+ * 注意:写入使用标准 JSON 格式(JSON5 的子集),
44
+ * 原始文件中的 JSON5 注释会丢失。这是已知限制。
45
+ */
46
+ save(): Promise<void>;
47
+ /** 保存并尝试触发热重载 */
48
+ saveAndReload(): Promise<void>;
49
+ private ensureRocketchatConfig;
50
+ }
51
+ export {};
52
+ //# sourceMappingURL=writer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"writer.d.ts","sourceRoot":"","sources":["../../src/config/writer.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EACV,uBAAuB,EACvB,aAAa,EACb,eAAe,EAChB,MAAM,oBAAoB,CAAC;AAE5B,6BAA6B;AAC7B,UAAU,cAAc;IACtB,MAAM,CAAC,EAAE;QACP,IAAI,CAAC,EAAE,aAAa,EAAE,CAAC;KACxB,CAAC;IACF,QAAQ,CAAC,EAAE,eAAe,EAAE,CAAC;IAC7B,QAAQ,CAAC,EAAE;QACT,UAAU,CAAC,EAAE,OAAO,CAAC,uBAAuB,CAAC,CAAC;QAC9C,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;KACxB,CAAC;IACF,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED,qBAAa,YAAY;IACvB,OAAO,CAAC,UAAU,CAAS;IAC3B,OAAO,CAAC,MAAM,CAAsB;gBAExB,UAAU,EAAE,MAAM;IAQ9B,uBAAuB;IACjB,UAAU,IAAI,OAAO,CAAC,cAAc,CAAC;IAiB3C,wBAAwB;IACxB,aAAa,IAAI,aAAa,EAAE;IAIhC,0BAA0B;IAC1B,mBAAmB,IAAI,OAAO,CAAC,uBAAuB,CAAC,GAAG,SAAS;IAInE,mCAAmC;IACnC,qBAAqB,IAAI,eAAe,EAAE;IAM1C,oBAAoB;IACpB,cAAc,IAAI,eAAe,EAAE;IAQnC,yBAAyB;IACzB,oBAAoB,CAAC,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI;IAwB3D,4BAA4B;IAC5B,aAAa,CACX,SAAS,EAAE,MAAM,EACjB,WAAW,EAAE,MAAM,EACnB,WAAW,CAAC,EAAE,MAAM,GACnB,IAAI;IAWP,+BAA+B;IAC/B,UAAU,CAAC,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,IAAI;IAqBpD,2BAA2B;IAC3B,QAAQ,CACN,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,MAAM,EAAE,EACd,cAAc,EAAE,OAAO,GACtB,IAAI;IAQP,cAAc;IACd,gBAAgB,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI;IAczC,WAAW;IACX,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI;IAO/B,2BAA2B;IAC3B,sBAAsB,IAAI,IAAI;IAgB9B;;;OAGG;IACG,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAS3B,iBAAiB;IACX,aAAa,IAAI,OAAO,CAAC,IAAI,CAAC;IAUpC,OAAO,CAAC,sBAAsB;CAS/B"}
@@ -0,0 +1,170 @@
1
+ // ============================================================
2
+ // OpenClaw 配置读写工具
3
+ // 安全读写 openclaw.json,只写入 channels.rocketchat 和 bindings
4
+ // ============================================================
5
+ import { readFile, writeFile } from "node:fs/promises";
6
+ import { existsSync } from "node:fs";
7
+ import JSON5 from "json5";
8
+ export class ConfigWriter {
9
+ configPath;
10
+ config = {};
11
+ constructor(configPath) {
12
+ this.configPath = configPath;
13
+ }
14
+ // ----------------------------------------------------------
15
+ // 读取
16
+ // ----------------------------------------------------------
17
+ /** 读取 openclaw.json */
18
+ async readConfig() {
19
+ if (!existsSync(this.configPath)) {
20
+ this.config = {};
21
+ return this.config;
22
+ }
23
+ try {
24
+ const content = await readFile(this.configPath, "utf-8");
25
+ this.config = JSON5.parse(content);
26
+ }
27
+ catch (err) {
28
+ throw new Error(`无法读取 openclaw.json: ${err.message}\n路径: ${this.configPath}`);
29
+ }
30
+ return this.config;
31
+ }
32
+ /** 获取已有 Agent 列表(只读) */
33
+ getAgentsList() {
34
+ return this.config.agents?.list || [];
35
+ }
36
+ /** 获取 Rocket.Chat 频道配置 */
37
+ getRocketchatConfig() {
38
+ return this.config.channels?.rocketchat;
39
+ }
40
+ /** 获取所有 rocketchat 相关的 bindings */
41
+ getRocketchatBindings() {
42
+ return (this.config.bindings || []).filter((b) => b.match?.channel === "rocketchat");
43
+ }
44
+ /** 获取所有 bindings */
45
+ getAllBindings() {
46
+ return this.config.bindings || [];
47
+ }
48
+ // ----------------------------------------------------------
49
+ // 写入 channels.rocketchat
50
+ // ----------------------------------------------------------
51
+ /** 设置基础配置(setup 命令调用) */
52
+ setRocketchatChannel(serverUrl, port) {
53
+ if (!this.config.channels) {
54
+ this.config.channels = {};
55
+ }
56
+ if (!this.config.channels.rocketchat) {
57
+ this.config.channels.rocketchat = {};
58
+ }
59
+ const rc = this.config.channels.rocketchat;
60
+ rc.enabled = true;
61
+ rc.serverUrl = serverUrl;
62
+ rc.port = port;
63
+ if (!rc.dmPolicy) {
64
+ rc.dmPolicy = "pairing";
65
+ }
66
+ if (!rc.accounts) {
67
+ rc.accounts = {};
68
+ }
69
+ if (!rc.groups) {
70
+ rc.groups = {};
71
+ }
72
+ }
73
+ /** 添加机器人账号(add-bot 命令调用) */
74
+ addBotAccount(accountId, botUsername, displayName) {
75
+ const rc = this.ensureRocketchatConfig();
76
+ if (!rc.accounts) {
77
+ rc.accounts = {};
78
+ }
79
+ rc.accounts[accountId] = {
80
+ botUsername,
81
+ ...(displayName ? { botDisplayName: displayName } : {}),
82
+ };
83
+ }
84
+ /** 添加 binding(add-bot 命令调用) */
85
+ addBinding(agentId, accountId) {
86
+ if (!this.config.bindings) {
87
+ this.config.bindings = [];
88
+ }
89
+ // 检查是否已存在
90
+ const exists = this.config.bindings.some((b) => b.agentId === agentId &&
91
+ b.match?.channel === "rocketchat" &&
92
+ b.match?.accountId === accountId);
93
+ if (!exists) {
94
+ this.config.bindings.push({
95
+ agentId,
96
+ match: { channel: "rocketchat", accountId },
97
+ });
98
+ }
99
+ }
100
+ /** 添加群组(add-group 命令调用) */
101
+ addGroup(name, bots, requireMention) {
102
+ const rc = this.ensureRocketchatConfig();
103
+ if (!rc.groups) {
104
+ rc.groups = {};
105
+ }
106
+ rc.groups[name] = { requireMention, bots };
107
+ }
108
+ /** 移除机器人账号 */
109
+ removeBotAccount(accountId) {
110
+ const rc = this.config.channels?.rocketchat;
111
+ if (rc?.accounts) {
112
+ delete rc.accounts[accountId];
113
+ }
114
+ // 同时移除对应的 bindings
115
+ if (this.config.bindings) {
116
+ this.config.bindings = this.config.bindings.filter((b) => !(b.match?.channel === "rocketchat" && b.match?.accountId === accountId));
117
+ }
118
+ }
119
+ /** 移除群组 */
120
+ removeGroup(name) {
121
+ const rc = this.config.channels?.rocketchat;
122
+ if (rc?.groups) {
123
+ delete rc.groups[name];
124
+ }
125
+ }
126
+ /** 清除所有 rocketchat 相关配置 */
127
+ removeRocketchatConfig() {
128
+ if (this.config.channels) {
129
+ delete this.config.channels.rocketchat;
130
+ }
131
+ // 移除 rocketchat 相关的 bindings
132
+ if (this.config.bindings) {
133
+ this.config.bindings = this.config.bindings.filter((b) => b.match?.channel !== "rocketchat");
134
+ }
135
+ }
136
+ // ----------------------------------------------------------
137
+ // 保存
138
+ // ----------------------------------------------------------
139
+ /** 保存到文件
140
+ * 注意:写入使用标准 JSON 格式(JSON5 的子集),
141
+ * 原始文件中的 JSON5 注释会丢失。这是已知限制。
142
+ */
143
+ async save() {
144
+ const content = JSON.stringify(this.config, null, 2);
145
+ // 原子写入:先写临时文件再重命名,防止写入中断导致文件损坏
146
+ const tmpPath = this.configPath + ".tmp";
147
+ await writeFile(tmpPath, content + "\n", "utf-8");
148
+ const { rename } = await import("node:fs/promises");
149
+ await rename(tmpPath, this.configPath);
150
+ }
151
+ /** 保存并尝试触发热重载 */
152
+ async saveAndReload() {
153
+ await this.save();
154
+ // 热重载:通过向 Gateway 发送信号(如果支持的话)
155
+ // OpenClaw 监听配置文件变化会自动重载
156
+ }
157
+ // ----------------------------------------------------------
158
+ // 内部
159
+ // ----------------------------------------------------------
160
+ ensureRocketchatConfig() {
161
+ if (!this.config.channels) {
162
+ this.config.channels = {};
163
+ }
164
+ if (!this.config.channels.rocketchat) {
165
+ this.config.channels.rocketchat = {};
166
+ }
167
+ return this.config.channels.rocketchat;
168
+ }
169
+ }
170
+ //# sourceMappingURL=writer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"writer.js","sourceRoot":"","sources":["../../src/config/writer.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,10 @@
1
+ /**
2
+ * 生成 docker-compose.yml 内容
3
+ * @param port Rocket.Chat 对外暴露的端口
4
+ */
5
+ export declare function generateComposeYaml(port: number): string;
6
+ /**
7
+ * 生成 .env 文件内容
8
+ */
9
+ export declare function generateEnvFile(port: number): string;
10
+ //# sourceMappingURL=compose.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compose.d.ts","sourceRoot":"","sources":["../../src/docker/compose.ts"],"names":[],"mappings":"AAIA;;;GAGG;AACH,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAyCxD;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAEpD"}
@@ -0,0 +1,56 @@
1
+ // ============================================================
2
+ // Docker Compose 配置文件生成
3
+ // ============================================================
4
+ /**
5
+ * 生成 docker-compose.yml 内容
6
+ * @param port Rocket.Chat 对外暴露的端口
7
+ */
8
+ export function generateComposeYaml(port) {
9
+ return `# Auto-generated by @openclaw-community/rocketchat plugin
10
+ # Do not edit manually
11
+
12
+ services:
13
+ rocketchat:
14
+ image: registry.rocket.chat/rocketchat/rocket.chat:latest
15
+ restart: unless-stopped
16
+ ports:
17
+ - "\${RC_PORT:-${port}}:3000"
18
+ environment:
19
+ MONGO_URL: "mongodb://mongodb:27017/rocketchat?replicaSet=rs0"
20
+ MONGO_OPLOG_URL: "mongodb://mongodb:27017/local?replicaSet=rs0"
21
+ ROOT_URL: "http://localhost:\${RC_PORT:-${port}}"
22
+ OVERWRITE_SETTING_Show_Setup_Wizard: "completed"
23
+ OVERWRITE_SETTING_Accounts_RegistrationForm: "Disabled"
24
+ depends_on:
25
+ mongodb:
26
+ condition: service_healthy
27
+
28
+ mongodb:
29
+ image: docker.io/bitnami/mongodb:7.0
30
+ restart: unless-stopped
31
+ volumes:
32
+ - mongodb_data:/bitnami/mongodb
33
+ environment:
34
+ MONGODB_REPLICA_SET_MODE: primary
35
+ MONGODB_REPLICA_SET_NAME: rs0
36
+ MONGODB_PORT_NUMBER: 27017
37
+ MONGODB_INITIAL_PRIMARY_HOST: mongodb
38
+ MONGODB_ADVERTISED_HOSTNAME: mongodb
39
+ ALLOW_EMPTY_PASSWORD: "yes"
40
+ healthcheck:
41
+ test: echo 'db.runCommand("ping").ok' | mongosh --quiet
42
+ interval: 10s
43
+ timeout: 5s
44
+ retries: 5
45
+
46
+ volumes:
47
+ mongodb_data:
48
+ `;
49
+ }
50
+ /**
51
+ * 生成 .env 文件内容
52
+ */
53
+ export function generateEnvFile(port) {
54
+ return `RC_PORT=${port}\n`;
55
+ }
56
+ //# sourceMappingURL=compose.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compose.js","sourceRoot":"","sources":["../../src/docker/compose.ts"],"names":[],"mappings":"AAAA,+DAA+D;AAC/D,wBAAwB;AACxB,+DAA+D;AAE/D;;;GAGG;AACH,MAAM,UAAU,mBAAmB,CAAC,IAAY;IAC9C,OAAO;;;;;;;;uBAQc,IAAI;;;;gDAIqB,IAAI;;;;;;;;;;;;;;;;;;;;;;;;;;;CA2BnD,CAAC;AACF,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,eAAe,CAAC,IAAY;IAC1C,OAAO,WAAW,IAAI,IAAI,CAAC;AAC7B,CAAC"}
@@ -0,0 +1,38 @@
1
+ import type { ContainerStatus } from "../rc-api/types.js";
2
+ export declare class DockerManager {
3
+ private composeDir;
4
+ constructor(composeDir: string);
5
+ /** 检查 Docker 是否已安装 */
6
+ isDockerInstalled(): Promise<{
7
+ installed: boolean;
8
+ version?: string;
9
+ }>;
10
+ /** 检查 Docker Compose 是否可用 */
11
+ isComposeInstalled(): Promise<{
12
+ installed: boolean;
13
+ version?: string;
14
+ }>;
15
+ /** 检查端口是否可用 */
16
+ isPortAvailable(port: number): Promise<boolean>;
17
+ /** 生成 docker-compose.yml 和 .env 文件 */
18
+ generateComposeFile(port: number): Promise<void>;
19
+ /** 启动容器 */
20
+ start(): Promise<void>;
21
+ /** 停止容器 */
22
+ stop(): Promise<void>;
23
+ /** 移除容器(可选删除卷) */
24
+ remove(deleteVolumes: boolean): Promise<void>;
25
+ /** 获取容器状态 */
26
+ getStatus(): Promise<ContainerStatus>;
27
+ /** 等待 Rocket.Chat 就绪(轮询 /api/v1/info) */
28
+ waitForReady(port: number, timeoutMs?: number, onProgress?: (msg: string) => void): Promise<void>;
29
+ /**
30
+ * 获取本机非 loopback IP 地址
31
+ * 优先物理网卡(en0/eth0/wlan0),跳过 Docker/VPN 等虚拟接口
32
+ */
33
+ getHostIp(): string;
34
+ /** 检查 compose 文件是否存在 */
35
+ composeFileExists(): boolean;
36
+ private compose;
37
+ }
38
+ //# sourceMappingURL=manager.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"manager.d.ts","sourceRoot":"","sources":["../../src/docker/manager.ts"],"names":[],"mappings":"AAYA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AAI1D,qBAAa,aAAa;IACxB,OAAO,CAAC,UAAU,CAAS;gBAEf,UAAU,EAAE,MAAM;IAQ9B,sBAAsB;IAChB,iBAAiB,IAAI,OAAO,CAAC;QAAE,SAAS,EAAE,OAAO,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;IAU5E,6BAA6B;IACvB,kBAAkB,IAAI,OAAO,CAAC;QAClC,SAAS,EAAE,OAAO,CAAC;QACnB,OAAO,CAAC,EAAE,MAAM,CAAC;KAClB,CAAC;IAaF,eAAe;IACT,eAAe,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAsBrD,sCAAsC;IAChC,mBAAmB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAoBtD,WAAW;IACL,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAI5B,WAAW;IACL,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAI3B,kBAAkB;IACZ,MAAM,CAAC,aAAa,EAAE,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC;IAQnD,aAAa;IACP,SAAS,IAAI,OAAO,CAAC,eAAe,CAAC;IAqC3C,yCAAyC;IACnC,YAAY,CAChB,IAAI,EAAE,MAAM,EACZ,SAAS,SAAS,EAClB,UAAU,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,GACjC,OAAO,CAAC,IAAI,CAAC;IA4BhB;;;OAGG;IACH,SAAS,IAAI,MAAM;IAsDnB,wBAAwB;IACxB,iBAAiB,IAAI,OAAO;YAQd,OAAO;CAQtB"}