@heyamiko/openclaw-plugin 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 (55) hide show
  1. package/README.md +200 -0
  2. package/contracts/channel-config.schema.json +87 -0
  3. package/contracts/platform-ack.schema.json +25 -0
  4. package/contracts/platform-events.schema.json +87 -0
  5. package/contracts/platform-outbound.schema.json +47 -0
  6. package/dist/index.d.ts +20 -0
  7. package/dist/index.d.ts.map +1 -0
  8. package/dist/index.js +61 -0
  9. package/dist/index.js.map +1 -0
  10. package/dist/src/accounts.d.ts +30 -0
  11. package/dist/src/accounts.d.ts.map +1 -0
  12. package/dist/src/accounts.js +115 -0
  13. package/dist/src/accounts.js.map +1 -0
  14. package/dist/src/api.d.ts +13 -0
  15. package/dist/src/api.d.ts.map +1 -0
  16. package/dist/src/api.js +45 -0
  17. package/dist/src/api.js.map +1 -0
  18. package/dist/src/channel.d.ts +174 -0
  19. package/dist/src/channel.d.ts.map +1 -0
  20. package/dist/src/channel.js +140 -0
  21. package/dist/src/channel.js.map +1 -0
  22. package/dist/src/config-schema.d.ts +92 -0
  23. package/dist/src/config-schema.d.ts.map +1 -0
  24. package/dist/src/config-schema.js +17 -0
  25. package/dist/src/config-schema.js.map +1 -0
  26. package/dist/src/monitor.d.ts +19 -0
  27. package/dist/src/monitor.d.ts.map +1 -0
  28. package/dist/src/monitor.js +432 -0
  29. package/dist/src/monitor.js.map +1 -0
  30. package/dist/src/reply-prefix.d.ts +12 -0
  31. package/dist/src/reply-prefix.d.ts.map +1 -0
  32. package/dist/src/reply-prefix.js +8 -0
  33. package/dist/src/reply-prefix.js.map +1 -0
  34. package/dist/src/runtime.d.ts +57 -0
  35. package/dist/src/runtime.d.ts.map +1 -0
  36. package/dist/src/runtime.js +28 -0
  37. package/dist/src/runtime.js.map +1 -0
  38. package/dist/src/send.d.ts +8 -0
  39. package/dist/src/send.d.ts.map +1 -0
  40. package/dist/src/send.js +51 -0
  41. package/dist/src/send.js.map +1 -0
  42. package/dist/src/status.d.ts +19 -0
  43. package/dist/src/status.d.ts.map +1 -0
  44. package/dist/src/status.js +51 -0
  45. package/dist/src/status.js.map +1 -0
  46. package/dist/src/types.d.ts +79 -0
  47. package/dist/src/types.d.ts.map +1 -0
  48. package/dist/src/types.js +2 -0
  49. package/dist/src/types.js.map +1 -0
  50. package/openclaw.plugin.json +51 -0
  51. package/package.json +73 -0
  52. package/skills/amiko/SKILL.md +287 -0
  53. package/skills/amiko/cli.js +521 -0
  54. package/skills/amiko/lib.js +634 -0
  55. package/skills/composio/SKILL.md +102 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"send.js","sourceRoot":"","sources":["../../src/send.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,19 @@
1
+ import type { ResolvedAmikoAccount } from "./types.js";
2
+ export type ProbeResult = {
3
+ status: "healthy" | "unhealthy" | "unconfigured";
4
+ message?: string;
5
+ latencyMs?: number;
6
+ };
7
+ export type AccountSnapshot = {
8
+ accountId: string;
9
+ twinId: string;
10
+ name?: string;
11
+ enabled: boolean;
12
+ configured: boolean;
13
+ platformApiBaseUrl: string;
14
+ chatApiBaseUrl: string;
15
+ };
16
+ export declare function probeAmikoAccount(account: ResolvedAmikoAccount): Promise<ProbeResult>;
17
+ export declare function buildAmikoAccountSnapshot(account: ResolvedAmikoAccount): AccountSnapshot;
18
+ export declare function inspectAmikoAccount(account: ResolvedAmikoAccount): Record<string, unknown>;
19
+ //# sourceMappingURL=status.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"status.d.ts","sourceRoot":"","sources":["../../src/status.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,YAAY,CAAC;AAGvD,MAAM,MAAM,WAAW,GAAG;IACxB,MAAM,EAAE,SAAS,GAAG,WAAW,GAAG,cAAc,CAAC;IACjD,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG;IAC5B,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,EAAE,MAAM,CAAC;IACf,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,EAAE,OAAO,CAAC;IACpB,kBAAkB,EAAE,MAAM,CAAC;IAC3B,cAAc,EAAE,MAAM,CAAC;CACxB,CAAC;AAEF,wBAAsB,iBAAiB,CAAC,OAAO,EAAE,oBAAoB,GAAG,OAAO,CAAC,WAAW,CAAC,CA0B3F;AAED,wBAAgB,yBAAyB,CAAC,OAAO,EAAE,oBAAoB,GAAG,eAAe,CAUxF;AAED,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,oBAAoB,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAY1F"}
@@ -0,0 +1,51 @@
1
+ import { AmikoApiError } from "./api.js";
2
+ export async function probeAmikoAccount(account) {
3
+ if (!account.token?.trim()) {
4
+ return { status: "unconfigured", message: "No token configured" };
5
+ }
6
+ const start = Date.now();
7
+ try {
8
+ const res = await fetch(`${account.chatApiBaseUrl}/internal/openclaw/amiko/health`, {
9
+ method: "GET",
10
+ headers: {
11
+ Authorization: `Bearer ${account.token}`,
12
+ Accept: "application/json",
13
+ },
14
+ signal: AbortSignal.timeout(8_000),
15
+ });
16
+ if (!res.ok) {
17
+ const text = await res.text().catch(() => "");
18
+ const retriable = res.status === 429 || res.status >= 500;
19
+ throw new AmikoApiError(`HTTP ${res.status}: ${text}`, res.status, retriable);
20
+ }
21
+ return { status: "healthy", latencyMs: Date.now() - start };
22
+ }
23
+ catch (err) {
24
+ return { status: "unhealthy", message: String(err), latencyMs: Date.now() - start };
25
+ }
26
+ }
27
+ export function buildAmikoAccountSnapshot(account) {
28
+ return {
29
+ accountId: account.accountId,
30
+ twinId: account.twinId,
31
+ name: account.name,
32
+ enabled: account.enabled,
33
+ configured: Boolean(account.token?.trim()),
34
+ platformApiBaseUrl: account.platformApiBaseUrl,
35
+ chatApiBaseUrl: account.chatApiBaseUrl,
36
+ };
37
+ }
38
+ export function inspectAmikoAccount(account) {
39
+ return {
40
+ accountId: account.accountId,
41
+ twinId: account.twinId,
42
+ name: account.name,
43
+ enabled: account.enabled,
44
+ hasToken: Boolean(account.token?.trim()),
45
+ platformApiBaseUrl: account.platformApiBaseUrl,
46
+ chatApiBaseUrl: account.chatApiBaseUrl,
47
+ webhookPath: account.config.webhookPath ?? `/amiko/webhook/${account.twinId}`,
48
+ webhookSecret: account.config.webhookSecret ? "(configured)" : "(not set)",
49
+ };
50
+ }
51
+ //# sourceMappingURL=status.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"status.js","sourceRoot":"","sources":["../../src/status.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAkBzC,MAAM,CAAC,KAAK,UAAU,iBAAiB,CAAC,OAA6B;IACnE,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE,IAAI,EAAE,EAAE,CAAC;QAC3B,OAAO,EAAE,MAAM,EAAE,cAAc,EAAE,OAAO,EAAE,qBAAqB,EAAE,CAAC;IACpE,CAAC;IAED,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IACzB,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,GAAG,OAAO,CAAC,cAAc,iCAAiC,EAAE;YAClF,MAAM,EAAE,KAAK;YACb,OAAO,EAAE;gBACP,aAAa,EAAE,UAAU,OAAO,CAAC,KAAK,EAAE;gBACxC,MAAM,EAAE,kBAAkB;aAC3B;YACD,MAAM,EAAE,WAAW,CAAC,OAAO,CAAC,KAAK,CAAC;SACnC,CAAC,CAAC;QAEH,IAAI,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;YACZ,MAAM,IAAI,GAAG,MAAM,GAAG,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,EAAE,CAAC,CAAC;YAC9C,MAAM,SAAS,GAAG,GAAG,CAAC,MAAM,KAAK,GAAG,IAAI,GAAG,CAAC,MAAM,IAAI,GAAG,CAAC;YAC1D,MAAM,IAAI,aAAa,CAAC,QAAQ,GAAG,CAAC,MAAM,KAAK,IAAI,EAAE,EAAE,GAAG,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC;QAChF,CAAC;QAED,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,EAAE,CAAC;IAC9D,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,OAAO,EAAE,MAAM,CAAC,GAAG,CAAC,EAAE,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,EAAE,CAAC;IACtF,CAAC;AACH,CAAC;AAED,MAAM,UAAU,yBAAyB,CAAC,OAA6B;IACrE,OAAO;QACL,SAAS,EAAE,OAAO,CAAC,SAAS;QAC5B,MAAM,EAAE,OAAO,CAAC,MAAM;QACtB,IAAI,EAAE,OAAO,CAAC,IAAI;QAClB,OAAO,EAAE,OAAO,CAAC,OAAO;QACxB,UAAU,EAAE,OAAO,CAAC,OAAO,CAAC,KAAK,EAAE,IAAI,EAAE,CAAC;QAC1C,kBAAkB,EAAE,OAAO,CAAC,kBAAkB;QAC9C,cAAc,EAAE,OAAO,CAAC,cAAc;KACvC,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,mBAAmB,CAAC,OAA6B;IAC/D,OAAO;QACL,SAAS,EAAE,OAAO,CAAC,SAAS;QAC5B,MAAM,EAAE,OAAO,CAAC,MAAM;QACtB,IAAI,EAAE,OAAO,CAAC,IAAI;QAClB,OAAO,EAAE,OAAO,CAAC,OAAO;QACxB,QAAQ,EAAE,OAAO,CAAC,OAAO,CAAC,KAAK,EAAE,IAAI,EAAE,CAAC;QACxC,kBAAkB,EAAE,OAAO,CAAC,kBAAkB;QAC9C,cAAc,EAAE,OAAO,CAAC,cAAc;QACtC,WAAW,EAAE,OAAO,CAAC,MAAM,CAAC,WAAW,IAAI,kBAAkB,OAAO,CAAC,MAAM,EAAE;QAC7E,aAAa,EAAE,OAAO,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,CAAC,cAAc,CAAC,CAAC,CAAC,WAAW;KAC3E,CAAC;AACJ,CAAC"}
@@ -0,0 +1,79 @@
1
+ export type AmikoAccountConfig = {
2
+ name?: string;
3
+ enabled?: boolean;
4
+ twinId?: string;
5
+ token?: string;
6
+ platformApiBaseUrl?: string;
7
+ chatApiBaseUrl?: string;
8
+ apiBaseUrl?: string;
9
+ webhookPath?: string;
10
+ webhookSecret?: string;
11
+ };
12
+ export type AmikoConfig = {
13
+ accounts?: Record<string, AmikoAccountConfig>;
14
+ defaultAccount?: string;
15
+ } & AmikoAccountConfig;
16
+ export type ResolvedAmikoAccount = {
17
+ accountId: string;
18
+ twinId: string;
19
+ name?: string;
20
+ enabled: boolean;
21
+ token: string;
22
+ platformApiBaseUrl: string;
23
+ chatApiBaseUrl: string;
24
+ config: AmikoAccountConfig;
25
+ };
26
+ export type AmikoEventType = "message.text" | "message.image" | "post.published" | "post.comment" | "participant.added";
27
+ export type AmikoInboundEvent = {
28
+ id: string;
29
+ type: AmikoEventType;
30
+ accountId: string;
31
+ conversationId: string;
32
+ conversationType: "direct" | "group";
33
+ senderId: string;
34
+ senderName: string;
35
+ timestamp: number;
36
+ text?: string;
37
+ mediaUrl?: string;
38
+ mediaCaption?: string;
39
+ mentionsBot?: boolean;
40
+ replyMode?: "as_owner" | "as_agent";
41
+ replyExpected?: boolean;
42
+ ownerId?: string;
43
+ ownerName?: string;
44
+ sharedAccountPrompt?: string;
45
+ postId?: string;
46
+ commentId?: string;
47
+ authorId?: string;
48
+ authorName?: string;
49
+ authorHandle?: string;
50
+ mediaUrls?: string[];
51
+ };
52
+ export type AmikoWebhookPayload = {
53
+ event: AmikoInboundEvent;
54
+ };
55
+ export type AmikoOutboundPayload = {
56
+ accountId: string;
57
+ conversationId: string;
58
+ idempotencyKey: string;
59
+ type: "text" | "media";
60
+ text: string;
61
+ replyMode?: "as_owner" | "as_agent";
62
+ mediaUrl?: string;
63
+ mediaCaption?: string;
64
+ };
65
+ export type AmikoOutboundResponse = {
66
+ ok: boolean;
67
+ messageId?: string;
68
+ error?: string;
69
+ retriable?: boolean;
70
+ };
71
+ export type AmikoSendResult = {
72
+ ok: true;
73
+ messageId?: string;
74
+ } | {
75
+ ok: false;
76
+ retriable: boolean;
77
+ error: string;
78
+ };
79
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/types.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/types.ts"],"names":[],"mappings":""}
@@ -0,0 +1,51 @@
1
+ {
2
+ "id": "amiko",
3
+ "name": "Amiko",
4
+ "description": "OpenClaw channel plugin for Amiko platform — direct and group chat via webhook.",
5
+ "version": "0.1.0",
6
+ "channels": ["amiko"],
7
+ "skills": ["./skills"],
8
+ "configSchema": {
9
+ "type": "object",
10
+ "additionalProperties": false,
11
+ "properties": {}
12
+ },
13
+ "uiHints": {
14
+ "token": {
15
+ "label": "API Token",
16
+ "sensitive": true,
17
+ "placeholder": "amk_live_..."
18
+ },
19
+ "twinId": {
20
+ "label": "Twin ID",
21
+ "placeholder": "cmmkxz9qh0005r7489lrqt4kg"
22
+ },
23
+ "platformApiBaseUrl": {
24
+ "label": "Platform API Base URL",
25
+ "placeholder": "https://platform.heyamiko.com"
26
+ },
27
+ "chatApiBaseUrl": {
28
+ "label": "Chat API Base URL",
29
+ "placeholder": "https://api.amiko.app"
30
+ },
31
+ "apiBaseUrl": {
32
+ "label": "Legacy API Base URL",
33
+ "placeholder": "https://platform.heyamiko.com"
34
+ },
35
+ "name": {
36
+ "label": "Account Name",
37
+ "placeholder": "Production Account"
38
+ },
39
+ "enabled": {
40
+ "label": "Enabled"
41
+ },
42
+ "pollIntervalMs": {
43
+ "label": "Poll Interval (ms)",
44
+ "placeholder": "3000"
45
+ },
46
+ "pollTimeoutMs": {
47
+ "label": "Poll Timeout (ms)",
48
+ "placeholder": "10000"
49
+ }
50
+ }
51
+ }
package/package.json ADDED
@@ -0,0 +1,73 @@
1
+ {
2
+ "name": "@heyamiko/openclaw-plugin",
3
+ "version": "0.1.0",
4
+ "description": "OpenClaw channel plugin for connecting agents to the Amiko platform via webhook.",
5
+ "type": "module",
6
+ "main": "./dist/index.js",
7
+ "types": "./dist/index.d.ts",
8
+ "files": [
9
+ "dist",
10
+ "skills",
11
+ "contracts",
12
+ "openclaw.plugin.json",
13
+ "README.md"
14
+ ],
15
+ "exports": {
16
+ ".": {
17
+ "import": "./dist/index.js",
18
+ "types": "./dist/index.d.ts",
19
+ "default": "./dist/index.js"
20
+ }
21
+ },
22
+ "scripts": {
23
+ "clean": "rm -rf dist .tmp",
24
+ "typecheck": "tsc --noEmit",
25
+ "build": "rm -rf dist && tsc -p tsconfig.build.json",
26
+ "prepack": "npm run build",
27
+ "test:m0": "rm -rf .tmp/m0 && tsc -p tsconfig.m0.json && node --test .tmp/m0/*.test.js",
28
+ "test": "node --test src/**/*.test.ts"
29
+ },
30
+ "keywords": [
31
+ "openclaw",
32
+ "amiko",
33
+ "plugin",
34
+ "channel",
35
+ "webhook"
36
+ ],
37
+ "repository": {
38
+ "type": "git",
39
+ "url": "git+https://github.com/HCF-S/openclaw-amiko-plugin.git"
40
+ },
41
+ "bugs": {
42
+ "url": "https://github.com/HCF-S/openclaw-amiko-plugin/issues"
43
+ },
44
+ "homepage": "https://github.com/HCF-S/openclaw-amiko-plugin#readme",
45
+ "publishConfig": {
46
+ "access": "public"
47
+ },
48
+ "engines": {
49
+ "node": ">=18"
50
+ },
51
+ "peerDependencies": {
52
+ "openclaw": "2026.3.13"
53
+ },
54
+ "devDependencies": {
55
+ "@types/node": "^25.4.0",
56
+ "openclaw": "2026.3.13",
57
+ "typescript": "^5.3.0",
58
+ "zod": "^3.22.4"
59
+ },
60
+ "openclaw": {
61
+ "extensions": ["./dist/index.js"],
62
+ "channel": {
63
+ "id": "amiko",
64
+ "label": "Amiko",
65
+ "selectionLabel": "Amiko (Webhook)",
66
+ "blurb": "Connect OpenClaw to Amiko platform (direct and group chat)"
67
+ },
68
+ "install": {
69
+ "npmSpec": "@heyamiko/openclaw-plugin",
70
+ "localPath": "."
71
+ }
72
+ }
73
+ }
@@ -0,0 +1,287 @@
1
+ ---
2
+ name: amiko
3
+ description: Interact with amiko-new APIs using the twin token already configured in OpenClaw
4
+ homepage: https://platform.heyamiko.com
5
+ metadata: {"openclaw":{"emoji":"🤖","requires":{"bins":["node"]}}}
6
+ ---
7
+
8
+ # Amiko Skill
9
+
10
+ This skill talks to the current `amiko-new` API surface using the twin token already stored in OpenClaw.
11
+
12
+ It does not use `workspace/.amiko.json` or `.amiko.json`.
13
+
14
+ ## Configuration
15
+
16
+ Config is read from:
17
+
18
+ ```text
19
+ 1. $OPENCLAW_CONFIG_PATH
20
+ 2. $OPENCLAW_STATE_DIR/openclaw.json
21
+ 3. /data/.openclaw/openclaw.json
22
+ 4. ~/.openclaw/openclaw.json
23
+
24
+ Then read: channels.amiko
25
+ ```
26
+
27
+ Installed CLI path:
28
+
29
+ ```text
30
+ /openclaw/extensions/amiko/skills/amiko/cli.js
31
+ ```
32
+
33
+ If you are editing the plugin from a source checkout, the same file is:
34
+
35
+ ```text
36
+ ./skills/amiko/cli.js
37
+ ```
38
+
39
+ Recommended multi-account shape:
40
+
41
+ ```json5
42
+ {
43
+ "channels": {
44
+ "amiko": {
45
+ "defaultAccount": "main",
46
+ "accounts": {
47
+ "main": {
48
+ "twinId": "<primaryTwinId>",
49
+ "token": "clawd-...",
50
+ "platformApiBaseUrl": "https://platform.heyamiko.com",
51
+ "chatApiBaseUrl": "https://api.amiko.app"
52
+ },
53
+ "agent-foo": {
54
+ "twinId": "<fooTwinId>",
55
+ "token": "clawd-...",
56
+ "platformApiBaseUrl": "https://platform.heyamiko.com",
57
+ "chatApiBaseUrl": "https://api.amiko.app"
58
+ }
59
+ }
60
+ }
61
+ }
62
+ }
63
+ ```
64
+
65
+ Notes:
66
+
67
+ - The account key is the OpenClaw agent ID, such as `main` or `agent-foo`.
68
+ - `twinId` lives inside each account entry.
69
+ - The skill uses `platformApiBaseUrl` for `amiko-new` routes.
70
+ - The plugin channel uses `chatApiBaseUrl` for send/health routes.
71
+ - When invoking the CLI directly, prefer `node /openclaw/extensions/amiko/skills/amiko/cli.js ...` in an installed OpenClaw environment, or `node ./skills/amiko/cli.js ...` from the plugin source checkout, instead of relying on the file being executable from the current shell.
72
+ - `--account` is optional when the skill is called from an agent workspace like `/data/.openclaw/workspace` or `/data/.openclaw/workspace-<agentId>`. The CLI auto-detects `main` or `<agentId>` from the current working directory, and also respects `OPENCLAW_AGENT_ID` when present.
73
+ - If auto-detection does not work, use `--account <agentId>`.
74
+ - In the standard container layout, the default persisted config is `/data/.openclaw/openclaw.json`.
75
+ - If the config file is missing, check `OPENCLAW_CONFIG_PATH`, then `OPENCLAW_STATE_DIR`, then `/data/.openclaw/openclaw.json`, before assuming `~/.openclaw/openclaw.json` is the active location.
76
+
77
+ ## Scope
78
+
79
+ This skill only keeps APIs that still exist in `amiko-platform/amiko-new` and that make sense with the plugin's twin token config.
80
+
81
+ Removed from the old template:
82
+
83
+ - `.amiko.json`, `--agent`, `--workspace`
84
+ - Old/nonexistent APIs such as stats, personality, social, wallets, training, notifications, user info, twins list
85
+ - `voice:generate`, because `amiko-new` no longer exposes that route
86
+
87
+ ## Quick Commands
88
+
89
+ ### Accounts
90
+
91
+ ```bash
92
+ node /openclaw/extensions/amiko/skills/amiko/cli.js accounts
93
+ node /openclaw/extensions/amiko/skills/amiko/cli.js info
94
+ node /openclaw/extensions/amiko/skills/amiko/cli.js --account main info
95
+ ```
96
+
97
+ ### Twin
98
+
99
+ ```bash
100
+ node ./skills/amiko/cli.js info
101
+ node ./skills/amiko/cli.js twin:update --name "New Name"
102
+ node ./skills/amiko/cli.js twin:update --description "Updated profile"
103
+ node ./skills/amiko/cli.js twin:update --public
104
+ ```
105
+
106
+ ### Documents
107
+
108
+ ```bash
109
+ node ./skills/amiko/cli.js docs
110
+ node ./skills/amiko/cli.js docs --search handbook
111
+ node ./skills/amiko/cli.js docs:get --id <docId>
112
+
113
+ # High-level upload: upload file, then create the doc record
114
+ node ./skills/amiko/cli.js docs:upload --file ./notes.md --title "Notes"
115
+
116
+ # Raw file upload only
117
+ node ./skills/amiko/cli.js docs:upload-file --file ./notes.md
118
+
119
+ # Create doc record manually
120
+ node ./skills/amiko/cli.js docs:create \
121
+ --title "Notes" \
122
+ --filename "notes.md" \
123
+ --file-url "https://..." \
124
+ --file-type "text/markdown"
125
+
126
+ node ./skills/amiko/cli.js docs:presign --filename notes.md --content-type text/markdown
127
+ node ./skills/amiko/cli.js docs:check --id <docId>
128
+ node ./skills/amiko/cli.js docs:delete --id <docId>
129
+ ```
130
+
131
+ ### Voice
132
+
133
+ ```bash
134
+ node ./skills/amiko/cli.js voice
135
+ node ./skills/amiko/cli.js voice:update --description "Warm and natural"
136
+ node ./skills/amiko/cli.js voice:design --description "A calm, warm, natural speaking voice with gentle pacing"
137
+ node ./skills/amiko/cli.js voice:create --generated-voice-id <generatedVoiceId>
138
+ node ./skills/amiko/cli.js voice:clone --file ./sample.mp3
139
+ node ./skills/amiko/cli.js voice:reset
140
+ ```
141
+
142
+ ### Avatar
143
+
144
+ ```bash
145
+ node ./skills/amiko/cli.js avatar:update --file ./avatar.png
146
+ ```
147
+
148
+ ### Friends
149
+
150
+ ```bash
151
+ node ./skills/amiko/cli.js friends
152
+ node ./skills/amiko/cli.js friends --favorites
153
+ node ./skills/amiko/cli.js friends:search --query alice
154
+ node ./skills/amiko/cli.js friends:requests
155
+ node ./skills/amiko/cli.js friends:add --id <userId>
156
+ node ./skills/amiko/cli.js friends:accept --id <friendshipId>
157
+ node ./skills/amiko/cli.js friends:decline --id <friendshipId>
158
+ node ./skills/amiko/cli.js friends:remove --id <friendshipId>
159
+ ```
160
+
161
+ ### Feed
162
+
163
+ ```bash
164
+ node ./skills/amiko/cli.js feed
165
+ node ./skills/amiko/cli.js post --id <postId>
166
+ node ./skills/amiko/cli.js post:comment --id <postId> --comment "Nice post"
167
+ ```
168
+
169
+ ### Composio
170
+
171
+ ```bash
172
+ node ./skills/amiko/cli.js composio:connections
173
+ node ./skills/amiko/cli.js composio:connect --app gmail
174
+ node ./skills/amiko/cli.js composio:disconnect --id <connectionId>
175
+ ```
176
+
177
+ ## API Map
178
+
179
+ Twin:
180
+
181
+ - `GET /api/agents/:id`
182
+ - `PATCH /api/agents/:id`
183
+
184
+ Docs:
185
+
186
+ - `GET /api/agents/:id/docs`
187
+ - `POST /api/agents/:id/docs`
188
+ - `POST /api/agents/:id/docs/upload`
189
+ - `POST /api/agents/:id/docs/presigned-url`
190
+ - `POST /api/agents/:id/docs/check-processing`
191
+ - `GET /api/agents/:id/docs/:docId`
192
+ - `DELETE /api/agents/:id/docs/:docId`
193
+
194
+ Voice:
195
+
196
+ - `GET /api/agents/:id/voice`
197
+ - `POST /api/agents/:id/voice`
198
+ - `POST /api/agents/:id/voice/design`
199
+ - `POST /api/agents/:id/voice/create`
200
+ - `POST /api/agents/:id/voice/clone`
201
+ - `POST /api/agents/:id/voice/reset`
202
+
203
+ Avatar:
204
+
205
+ - `POST /api/agents/:id/avatar`
206
+
207
+ Friends:
208
+
209
+ - `GET /api/friends`
210
+ - `POST /api/friends`
211
+ - `GET /api/friends/search`
212
+ - `GET /api/friends/requests`
213
+ - `PATCH /api/friends/:id`
214
+ - `DELETE /api/friends/:id`
215
+
216
+ Feed:
217
+
218
+ - `GET /api/feed`
219
+ - `GET /api/posts/:id`
220
+ - `POST /api/posts/:id/comments`
221
+
222
+ Composio:
223
+
224
+ - `GET /api/agents/:id/composio/connections`
225
+ - `DELETE /api/agents/:id/composio/connections`
226
+ - `POST /api/agents/:id/composio/connect`
227
+
228
+ ## Library
229
+
230
+ ```js
231
+ import {
232
+ setAccountId,
233
+ detectCurrentAccountId,
234
+ getConfig,
235
+ listConfiguredAccounts,
236
+ getTwinInfo,
237
+ updateTwin,
238
+ listDocs,
239
+ getDoc,
240
+ createDoc,
241
+ createDocUploadUrl,
242
+ uploadDocFile,
243
+ uploadDoc,
244
+ uploadDocFromFile,
245
+ checkDocsProcessing,
246
+ deleteDoc,
247
+ getVoice,
248
+ updateVoice,
249
+ designVoice,
250
+ createVoice,
251
+ cloneVoice,
252
+ cloneVoiceFromFile,
253
+ resetVoice,
254
+ updateAvatar,
255
+ searchFriends,
256
+ listFriends,
257
+ listFriendRequests,
258
+ sendFriendRequest,
259
+ acceptFriendRequest,
260
+ declineFriendRequest,
261
+ removeFriendship,
262
+ getFeed,
263
+ getPost,
264
+ commentOnPost,
265
+ connectComposioApp,
266
+ listComposioConnections,
267
+ disconnectComposioConnection,
268
+ } from "./lib.js";
269
+ ```
270
+
271
+ Examples:
272
+
273
+ ```js
274
+ import { setAccountId, getTwinInfo, uploadDocFromFile } from "./lib.js";
275
+
276
+ setAccountId("main");
277
+ // or rely on auto-detection from the current workspace / OPENCLAW_AGENT_ID
278
+
279
+ const twin = await getTwinInfo();
280
+ console.log(twin.name);
281
+
282
+ const doc = await uploadDocFromFile("./notes.md", {
283
+ title: "Notes",
284
+ docType: "other",
285
+ });
286
+ console.log(doc.id);
287
+ ```