skyloom 1.21.0 → 1.23.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.
@@ -18,6 +18,9 @@ const http_1 = require("http");
18
18
  const logger_1 = require("../core/logger");
19
19
  const factory_1 = require("../core/factory");
20
20
  const registry_1 = require("./registry");
21
+ const types_1 = require("./types");
22
+ const helpers_1 = require("./helpers");
23
+ const vision_1 = require("./vision");
21
24
  const log = (0, logger_1.getLogger)('gateway');
22
25
  /** Collect the full request body. */
23
26
  async function readBody(req) {
@@ -27,25 +30,125 @@ async function readBody(req) {
27
30
  return Buffer.concat(chunks);
28
31
  }
29
32
  /** Run an agent turn for an inbound message and collect the final text reply. */
30
- async function runAgent(ctx, adapter, msg) {
33
+ /** Build the agent prompt: text + media description + any vision result. */
34
+ function buildPrompt(msg, canSendMedia, visionText) {
35
+ const parts = [];
36
+ const mediaDesc = (0, types_1.describeMedia)(msg.media);
37
+ if (msg.text)
38
+ parts.push(msg.text);
39
+ if (mediaDesc)
40
+ parts.push(`(用户发送了媒体: ${mediaDesc})`);
41
+ if (visionText)
42
+ parts.push(`(图片内容识别: ${visionText})`);
43
+ if (canSendMedia) {
44
+ parts.push('(若需回发图片或文件,在回复中用 Markdown 图片 ![说明](路径或URL) 或 [[file:路径或URL]] 表示,路径可为本地文件或 http(s) 链接。)');
45
+ }
46
+ return parts.join('\n\n') || msg.text;
47
+ }
48
+ /** Download inbound images and run vision over them. Returns null if disabled. */
49
+ async function visionForMessage(ctx, adapter, msg) {
50
+ const chCfg = (ctx.config.channels || {})[adapter.id] || {};
51
+ const llmCfg = ctx.config.llm || {};
52
+ if (chCfg.vision === false)
53
+ return null;
54
+ const model = chCfg.visionModel || llmCfg.vision_model || llmCfg.visionModel;
55
+ if (!model)
56
+ return null; // vision is opt-in: requires a configured model
57
+ const images = (msg.media || []).filter((m) => m.kind === 'image');
58
+ if (!images.length || !adapter.fetchMedia)
59
+ return null;
60
+ const loaded = [];
61
+ for (const att of images.slice(0, 4)) {
62
+ try {
63
+ const got = await adapter.fetchMedia(att, msg);
64
+ if (got)
65
+ loaded.push({ data: got.data, filename: att.filename || 'image', contentType: got.contentType });
66
+ }
67
+ catch (e) {
68
+ log.warn('vision_fetch_failed', { channel: adapter.id, error: String(e) });
69
+ }
70
+ }
71
+ if (!loaded.length)
72
+ return null;
73
+ return (0, vision_1.describeImages)(loaded, { model });
74
+ }
75
+ /** Resolve the agent for a channel message. */
76
+ function resolveAgent(ctx, adapter) {
31
77
  const cfgChannels = ctx.config.channels || {};
32
78
  const agentName = cfgChannels[adapter.id]?.agent || adapter.defaultAgent || 'fair';
33
- const agent = ctx.agentMap.get(agentName) || ctx.agentMap.get('fair') || [...ctx.agentMap.values()][0];
79
+ return ctx.agentMap.get(agentName) || ctx.agentMap.get('fair') || [...ctx.agentMap.values()][0];
80
+ }
81
+ /** Dispatch one inbound message to its agent and deliver the reply. */
82
+ async function dispatch(ctx, adapter, msg) {
83
+ const agent = resolveAgent(ctx, adapter);
34
84
  if (!agent)
35
85
  throw new Error('no agent available');
36
86
  await agent.init();
87
+ const visionText = await visionForMessage(ctx, adapter, msg);
88
+ const prompt = buildPrompt(msg, !!adapter.sendMedia, visionText);
89
+ // Streaming path: stream content chunks straight to the adapter (e.g. a Feishu
90
+ // card patched as text arrives). Falls back to collect-then-send otherwise.
91
+ const cfgStreaming = (ctx.config.channels || {})[adapter.id]?.streaming !== false;
92
+ if (adapter.sendStreaming && cfgStreaming) {
93
+ let full = '';
94
+ async function* contentChunks() {
95
+ try {
96
+ for await (const ev of agent.chatStream(prompt)) {
97
+ if (ev.type === 'content') {
98
+ const t = ev.text;
99
+ full += t;
100
+ yield t;
101
+ }
102
+ }
103
+ }
104
+ catch (e) {
105
+ log.warn('gateway_agent_failed', { channel: adapter.id, error: String(e) });
106
+ yield `\n[出错了] ${String(e)}`;
107
+ }
108
+ }
109
+ await adapter.sendStreaming(msg.replyTo, contentChunks());
110
+ // After streaming the text, deliver any media the agent referenced.
111
+ await deliverMedia(adapter, msg, full);
112
+ return;
113
+ }
37
114
  let text = '';
38
115
  try {
39
- for await (const ev of agent.chatStream(msg.text)) {
116
+ for await (const ev of agent.chatStream(prompt)) {
40
117
  if (ev.type === 'content')
41
118
  text += ev.text;
42
119
  }
43
120
  }
44
121
  catch (e) {
45
122
  log.warn('gateway_agent_failed', { channel: adapter.id, error: String(e) });
46
- return `[出错了] ${String(e)}`;
123
+ text = `[出错了] ${String(e)}`;
124
+ }
125
+ // Non-streaming: split out media so the text message is clean.
126
+ if (adapter.sendMedia) {
127
+ const parsed = (0, types_1.parseReply)(text);
128
+ await adapter.send(msg.replyTo, parsed.text || '(无回复)');
129
+ await deliverMedia(adapter, msg, text, parsed.media);
130
+ }
131
+ else {
132
+ await adapter.send(msg.replyTo, text.trim() || '(无回复)');
133
+ }
134
+ }
135
+ /** Upload+send any media the agent referenced in its reply. Best-effort. */
136
+ async function deliverMedia(adapter, msg, fullText, pre) {
137
+ if (!adapter.sendMedia)
138
+ return;
139
+ const media = pre ?? (0, types_1.parseReply)(fullText).media;
140
+ for (const item of media) {
141
+ if (!(0, helpers_1.isSendableSrc)(item.src)) {
142
+ log.warn('gateway_media_unsendable', { channel: adapter.id, src: item.src });
143
+ continue;
144
+ }
145
+ try {
146
+ await adapter.sendMedia(msg.replyTo, item);
147
+ }
148
+ catch (e) {
149
+ log.warn('gateway_send_media_failed', { channel: adapter.id, src: item.src, error: String(e) });
150
+ }
47
151
  }
48
- return text.trim() || '(无回复)';
49
152
  }
50
153
  async function startGateway(opts = {}) {
51
154
  const ctx = (0, factory_1.createSystemContext)();
@@ -107,15 +210,7 @@ async function startGateway(opts = {}) {
107
210
  // Route to an agent and deliver the reply asynchronously (after the ack).
108
211
  if (outcome.message) {
109
212
  const msg = outcome.message;
110
- void (async () => {
111
- try {
112
- const reply = await runAgent(ctx, adapter, msg);
113
- await adapter.send(msg.replyTo, reply);
114
- }
115
- catch (e) {
116
- log.warn('gateway_dispatch_failed', { channel: adapter.id, error: String(e) });
117
- }
118
- })();
213
+ void dispatch(ctx, adapter, msg).catch((e) => log.warn('gateway_dispatch_failed', { channel: adapter.id, error: String(e) }));
119
214
  }
120
215
  }
121
216
  catch (e) {
@@ -1 +1 @@
1
- {"version":3,"file":"gateway.js","sourceRoot":"","sources":["../../src/gateway/gateway.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"gateway.js","sourceRoot":"","sources":["../../src/gateway/gateway.ts"],"names":[],"mappings":"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"}
@@ -19,6 +19,29 @@ export declare function getJson(url: string, opts?: {
19
19
  headers?: Record<string, string>;
20
20
  timeoutMs?: number;
21
21
  }): Promise<any>;
22
+ /** A loaded binary plus its filename, ready to upload. */
23
+ export interface LoadedMedia {
24
+ data: Buffer;
25
+ filename: string;
26
+ contentType?: string;
27
+ }
28
+ /**
29
+ * Load media bytes from a local filesystem path or an http(s) URL. Local paths
30
+ * are read directly; remote URLs are fetched (capped at 30 MiB to avoid
31
+ * pulling something huge into memory). Throws if the source can't be loaded.
32
+ */
33
+ export declare function loadMedia(src: string): Promise<LoadedMedia>;
34
+ /** Is this a sendable media source (http(s) URL or an existing local file)? */
35
+ export declare function isSendableSrc(src: string): boolean;
36
+ /** POST multipart/form-data (Node 18+ FormData/Blob), return parsed JSON. */
37
+ export declare function postMultipart(url: string, fields: Record<string, string | {
38
+ data: Buffer;
39
+ filename: string;
40
+ contentType?: string;
41
+ }>, opts?: {
42
+ headers?: Record<string, string>;
43
+ timeoutMs?: number;
44
+ }): Promise<any>;
22
45
  /**
23
46
  * A small token cache: fetch an access token via `fetcher`, cache it until it
24
47
  * is near expiry, and refresh transparently. Channels (Feishu/WeCom) all need
@@ -1 +1 @@
1
- {"version":3,"file":"helpers.d.ts","sourceRoot":"","sources":["../../src/gateway/helpers.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAIH;;;;GAIG;AACH,wBAAgB,aAAa,CAC3B,KAAK,EAAE,OAAO,EACd,GAAG,EAAE,MAAM,CAAC,UAAU,EACtB,WAAW,CAAC,EAAE,MAAM,GACnB,MAAM,GAAG,SAAS,CAcpB;AAED,wDAAwD;AACxD,wBAAsB,QAAQ,CAC5B,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,GAAG,EACT,IAAI,CAAC,EAAE;IAAE,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAAC,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,GAC9D,OAAO,CAAC,GAAG,CAAC,CAOd;AAED,uDAAuD;AACvD,wBAAsB,OAAO,CAC3B,GAAG,EAAE,MAAM,EACX,IAAI,CAAC,EAAE;IAAE,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAAC,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,GAC9D,OAAO,CAAC,GAAG,CAAC,CAOd;AAED;;;;GAIG;AACH,qBAAa,UAAU;IAGT,OAAO,CAAC,OAAO;IAF3B,OAAO,CAAC,KAAK,CAAuB;IACpC,OAAO,CAAC,SAAS,CAAK;gBACF,OAAO,EAAE,MAAM,OAAO,CAAC;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,YAAY,EAAE,MAAM,CAAA;KAAE,CAAC;IAE7E,GAAG,IAAI,OAAO,CAAC,MAAM,CAAC;IAS5B,0DAA0D;IAC1D,UAAU,IAAI,IAAI;CACnB"}
1
+ {"version":3,"file":"helpers.d.ts","sourceRoot":"","sources":["../../src/gateway/helpers.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAMH;;;;GAIG;AACH,wBAAgB,aAAa,CAC3B,KAAK,EAAE,OAAO,EACd,GAAG,EAAE,MAAM,CAAC,UAAU,EACtB,WAAW,CAAC,EAAE,MAAM,GACnB,MAAM,GAAG,SAAS,CAcpB;AAED,wDAAwD;AACxD,wBAAsB,QAAQ,CAC5B,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,GAAG,EACT,IAAI,CAAC,EAAE;IAAE,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAAC,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,GAC9D,OAAO,CAAC,GAAG,CAAC,CAOd;AAED,uDAAuD;AACvD,wBAAsB,OAAO,CAC3B,GAAG,EAAE,MAAM,EACX,IAAI,CAAC,EAAE;IAAE,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAAC,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,GAC9D,OAAO,CAAC,GAAG,CAAC,CAOd;AAED,0DAA0D;AAC1D,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED;;;;GAIG;AACH,wBAAsB,SAAS,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,WAAW,CAAC,CAkBjE;AAED,+EAA+E;AAC/E,wBAAgB,aAAa,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAGlD;AAED,6EAA6E;AAC7E,wBAAsB,aAAa,CACjC,GAAG,EAAE,MAAM,EACX,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAC;IAAC,WAAW,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,EACzF,IAAI,CAAC,EAAE;IAAE,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAAC,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,GAC9D,OAAO,CAAC,GAAG,CAAC,CAad;AAED;;;;GAIG;AACH,qBAAa,UAAU;IAGT,OAAO,CAAC,OAAO;IAF3B,OAAO,CAAC,KAAK,CAAuB;IACpC,OAAO,CAAC,SAAS,CAAK;gBACF,OAAO,EAAE,MAAM,OAAO,CAAC;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,YAAY,EAAE,MAAM,CAAA;KAAE,CAAC;IAE7E,GAAG,IAAI,OAAO,CAAC,MAAM,CAAC;IAS5B,0DAA0D;IAC1D,UAAU,IAAI,IAAI;CACnB"}
@@ -4,6 +4,39 @@
4
4
  * fallback), and a tiny JSON HTTP client. Kept dependency-light (axios is
5
5
  * already a project dep) and injectable-free — adapters call these directly.
6
6
  */
7
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
8
+ if (k2 === undefined) k2 = k;
9
+ var desc = Object.getOwnPropertyDescriptor(m, k);
10
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
11
+ desc = { enumerable: true, get: function() { return m[k]; } };
12
+ }
13
+ Object.defineProperty(o, k2, desc);
14
+ }) : (function(o, m, k, k2) {
15
+ if (k2 === undefined) k2 = k;
16
+ o[k2] = m[k];
17
+ }));
18
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
19
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
20
+ }) : function(o, v) {
21
+ o["default"] = v;
22
+ });
23
+ var __importStar = (this && this.__importStar) || (function () {
24
+ var ownKeys = function(o) {
25
+ ownKeys = Object.getOwnPropertyNames || function (o) {
26
+ var ar = [];
27
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
28
+ return ar;
29
+ };
30
+ return ownKeys(o);
31
+ };
32
+ return function (mod) {
33
+ if (mod && mod.__esModule) return mod;
34
+ var result = {};
35
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
36
+ __setModuleDefault(result, mod);
37
+ return result;
38
+ };
39
+ })();
7
40
  var __importDefault = (this && this.__importDefault) || function (mod) {
8
41
  return (mod && mod.__esModule) ? mod : { "default": mod };
9
42
  };
@@ -12,7 +45,12 @@ exports.TokenCache = void 0;
12
45
  exports.resolveSecret = resolveSecret;
13
46
  exports.postJson = postJson;
14
47
  exports.getJson = getJson;
48
+ exports.loadMedia = loadMedia;
49
+ exports.isSendableSrc = isSendableSrc;
50
+ exports.postMultipart = postMultipart;
15
51
  const axios_1 = __importDefault(require("axios"));
52
+ const fs = __importStar(require("fs"));
53
+ const path = __importStar(require("path"));
16
54
  /**
17
55
  * Resolve a secret/config value. Accepts a literal string, or an env-ref object
18
56
  * `{ source: 'env', id: 'NAME' }` (OpenClaw-compatible), falling back to the
@@ -54,6 +92,58 @@ async function getJson(url, opts) {
54
92
  });
55
93
  return res.data;
56
94
  }
95
+ /**
96
+ * Load media bytes from a local filesystem path or an http(s) URL. Local paths
97
+ * are read directly; remote URLs are fetched (capped at 30 MiB to avoid
98
+ * pulling something huge into memory). Throws if the source can't be loaded.
99
+ */
100
+ async function loadMedia(src) {
101
+ if (/^https?:\/\//i.test(src)) {
102
+ const res = await axios_1.default.get(src, {
103
+ responseType: 'arraybuffer',
104
+ timeout: 30000,
105
+ maxContentLength: 30 * 1024 * 1024,
106
+ validateStatus: (s) => s >= 200 && s < 300,
107
+ });
108
+ const urlName = path.basename(new URL(src).pathname) || 'file';
109
+ const ct = res.headers['content-type'];
110
+ return {
111
+ data: Buffer.from(res.data),
112
+ filename: urlName,
113
+ contentType: typeof ct === 'string' ? ct : undefined,
114
+ };
115
+ }
116
+ const data = fs.readFileSync(src); // throws ENOENT if missing — caller handles
117
+ return { data, filename: path.basename(src) };
118
+ }
119
+ /** Is this a sendable media source (http(s) URL or an existing local file)? */
120
+ function isSendableSrc(src) {
121
+ if (/^https?:\/\//i.test(src))
122
+ return true;
123
+ try {
124
+ return fs.existsSync(src) && fs.statSync(src).isFile();
125
+ }
126
+ catch {
127
+ return false;
128
+ }
129
+ }
130
+ /** POST multipart/form-data (Node 18+ FormData/Blob), return parsed JSON. */
131
+ async function postMultipart(url, fields, opts) {
132
+ const form = new FormData();
133
+ for (const [k, v] of Object.entries(fields)) {
134
+ if (typeof v === 'string')
135
+ form.append(k, v);
136
+ else
137
+ form.append(k, new Blob([v.data], v.contentType ? { type: v.contentType } : undefined), v.filename);
138
+ }
139
+ const res = await axios_1.default.post(url, form, {
140
+ headers: { ...(opts?.headers || {}) },
141
+ timeout: opts?.timeoutMs ?? 30000,
142
+ maxBodyLength: Infinity,
143
+ validateStatus: (s) => s >= 200 && s < 300,
144
+ });
145
+ return res.data;
146
+ }
57
147
  /**
58
148
  * A small token cache: fetch an access token via `fetcher`, cache it until it
59
149
  * is near expiry, and refresh transparently. Channels (Feishu/WeCom) all need
@@ -1 +1 @@
1
- {"version":3,"file":"helpers.js","sourceRoot":"","sources":["../../src/gateway/helpers.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"helpers.js","sourceRoot":"","sources":["../../src/gateway/helpers.ts"],"names":[],"mappings":"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"}
@@ -22,9 +22,48 @@ export interface InboundMessage {
22
22
  text: string;
23
23
  /** Where to send the reply (channel-specific opaque target). */
24
24
  replyTo: ReplyTarget;
25
+ /** Media attachments on this message (image / audio / file / …). */
26
+ media?: MediaAttachment[];
25
27
  /** Raw event for adapters that need more than the normalized fields. */
26
28
  raw?: unknown;
27
29
  }
30
+ /** A non-text attachment, normalized across channels. */
31
+ export interface MediaAttachment {
32
+ kind: 'image' | 'audio' | 'video' | 'file' | 'sticker' | 'other';
33
+ /** Channel-specific id/key used to fetch the binary (image_key, media_id, url…). */
34
+ ref?: string;
35
+ /** Original filename, when the platform provides one. */
36
+ filename?: string;
37
+ /** MIME type, when known. */
38
+ mimeType?: string;
39
+ /** Direct URL, when the platform provides one. */
40
+ url?: string;
41
+ }
42
+ /** An outbound media item the agent wants to send (parsed from its reply). */
43
+ export interface OutboundMedia {
44
+ kind: 'image' | 'file';
45
+ /** Local filesystem path or http(s) URL to the binary. */
46
+ src: string;
47
+ /** Optional caption / alt text. */
48
+ alt?: string;
49
+ }
50
+ /** The result of splitting an agent reply into plain text + outbound media. */
51
+ export interface ParsedReply {
52
+ text: string;
53
+ media: OutboundMedia[];
54
+ }
55
+ /**
56
+ * Parse media directives out of an agent's reply so channels can upload+send
57
+ * them. Recognized forms (stripped from the returned text):
58
+ * - Markdown image: ![alt](src)
59
+ * - Explicit image: [[image:src]] or [[image:src|alt]]
60
+ * - Explicit file: [[file:src]] or [[file:src|alt]]
61
+ * `src` is a local path or http(s) URL. Only http(s) and existing local files
62
+ * are treated as media; anything else is left in the text untouched.
63
+ */
64
+ export declare function parseReply(reply: string): ParsedReply;
65
+ /** Render a media list into a compact, model-readable description line. */
66
+ export declare function describeMedia(media: MediaAttachment[] | undefined): string;
28
67
  /** Opaque, channel-specific destination for an outbound reply. */
29
68
  export interface ReplyTarget {
30
69
  channel: string;
@@ -75,6 +114,29 @@ export interface ChannelAdapter {
75
114
  handleWebhook(req: RawRequest): Promise<WebhookOutcome>;
76
115
  /** Send a text reply back to the channel. */
77
116
  send(target: ReplyTarget, text: string): Promise<void>;
117
+ /**
118
+ * Optional streaming reply: consume the agent's text chunks and render them
119
+ * progressively (e.g. a Feishu card patched as text accumulates). When an
120
+ * adapter implements this, the gateway prefers it over `send`. Implementations
121
+ * should throttle their own updates and tolerate an empty/aborted stream.
122
+ */
123
+ sendStreaming?(target: ReplyTarget, chunks: AsyncIterable<string>): Promise<void>;
124
+ /**
125
+ * Optional: upload and send an image or file. When an adapter implements this,
126
+ * the gateway extracts media directives from the agent's reply (parseReply)
127
+ * and delivers them after the text. Adapters without it simply keep the
128
+ * media reference in the text.
129
+ */
130
+ sendMedia?(target: ReplyTarget, item: OutboundMedia): Promise<void>;
131
+ /**
132
+ * Optional: download an inbound media attachment's bytes so the gateway can
133
+ * run vision over an image. `att` is one entry from InboundMessage.media.
134
+ * Returns the binary or null if it can't be fetched.
135
+ */
136
+ fetchMedia?(att: MediaAttachment, msg: InboundMessage): Promise<{
137
+ data: Buffer;
138
+ contentType?: string;
139
+ } | null>;
78
140
  }
79
141
  /** Factory signature: build an adapter from its config block (or null if disabled/misconfigured). */
80
142
  export type ChannelFactory = (cfg: any, env: NodeJS.ProcessEnv) => ChannelAdapter | null;
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/gateway/types.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,MAAM,CAAC;AAEhD,qDAAqD;AACrD,MAAM,WAAW,cAAc;IAC7B,iCAAiC;IACjC,OAAO,EAAE,MAAM,CAAC;IAChB,+EAA+E;IAC/E,cAAc,EAAE,MAAM,CAAC;IACvB,sCAAsC;IACtC,MAAM,EAAE,MAAM,CAAC;IACf,wEAAwE;IACxE,IAAI,EAAE,MAAM,CAAC;IACb,gEAAgE;IAChE,OAAO,EAAE,WAAW,CAAC;IACrB,wEAAwE;IACxE,GAAG,CAAC,EAAE,OAAO,CAAC;CACf;AAED,kEAAkE;AAClE,MAAM,WAAW,WAAW;IAC1B,OAAO,EAAE,MAAM,CAAC;IAChB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED;;;;;;;;GAQG;AACH,MAAM,WAAW,cAAc;IAC7B,QAAQ,CAAC,EAAE,YAAY,CAAC;IACxB,OAAO,CAAC,EAAE,cAAc,CAAC;CAC1B;AAED,MAAM,WAAW,YAAY;IAC3B,MAAM,EAAE,MAAM,CAAC;IACf,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,mEAAmE;AACnE,MAAM,WAAW,UAAU;IACzB,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,mBAAmB,CAAC;IAC7B,KAAK,EAAE,eAAe,CAAC;IACvB,IAAI,EAAE,MAAM,CAAC;CACd;AAED,6EAA6E;AAC7E,MAAM,WAAW,cAAc;IAC7B,mEAAmE;IACnE,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,mCAAmC;IACnC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,gFAAgF;IAChF,QAAQ,CAAC,YAAY,CAAC,EAAE,MAAM,CAAC;IAE/B,sEAAsE;IACtE,KAAK,CAAC,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;IACxB,6CAA6C;IAC7C,IAAI,CAAC,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;IAEvB;;;;OAIG;IACH,aAAa,CAAC,GAAG,EAAE,UAAU,GAAG,OAAO,CAAC,cAAc,CAAC,CAAC;IAExD,6CAA6C;IAC7C,IAAI,CAAC,MAAM,EAAE,WAAW,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CACxD;AAED,qGAAqG;AACrG,MAAM,MAAM,cAAc,GAAG,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,MAAM,CAAC,UAAU,KAAK,cAAc,GAAG,IAAI,CAAC"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/gateway/types.ts"],"names":[],"mappings":"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"}
@@ -11,4 +11,41 @@
11
11
  * stays platform-neutral.
12
12
  */
13
13
  Object.defineProperty(exports, "__esModule", { value: true });
14
+ exports.parseReply = parseReply;
15
+ exports.describeMedia = describeMedia;
16
+ /**
17
+ * Parse media directives out of an agent's reply so channels can upload+send
18
+ * them. Recognized forms (stripped from the returned text):
19
+ * - Markdown image: ![alt](src)
20
+ * - Explicit image: [[image:src]] or [[image:src|alt]]
21
+ * - Explicit file: [[file:src]] or [[file:src|alt]]
22
+ * `src` is a local path or http(s) URL. Only http(s) and existing local files
23
+ * are treated as media; anything else is left in the text untouched.
24
+ */
25
+ function parseReply(reply) {
26
+ const media = [];
27
+ let text = reply;
28
+ // [[image:src|alt]] / [[file:src|alt]]
29
+ text = text.replace(/\[\[(image|file):([^\]|]+)(?:\|([^\]]*))?\]\]/gi, (_m, kind, src, alt) => {
30
+ media.push({ kind: kind.toLowerCase(), src: String(src).trim(), alt: alt ? String(alt).trim() : undefined });
31
+ return '';
32
+ });
33
+ // Markdown images: ![alt](src)
34
+ text = text.replace(/!\[([^\]]*)\]\(([^)\s]+)(?:\s+"[^"]*")?\)/g, (_m, alt, src) => {
35
+ media.push({ kind: 'image', src: String(src).trim(), alt: alt ? String(alt).trim() : undefined });
36
+ return '';
37
+ });
38
+ return { text: text.replace(/\n{3,}/g, '\n\n').trim(), media };
39
+ }
40
+ /** Render a media list into a compact, model-readable description line. */
41
+ function describeMedia(media) {
42
+ if (!media || media.length === 0)
43
+ return '';
44
+ const parts = media.map((m) => {
45
+ const label = m.filename || m.ref || m.url || '';
46
+ const tag = label ? `${m.kind}: ${label}` : m.kind;
47
+ return `[${tag}]`;
48
+ });
49
+ return parts.join(' ');
50
+ }
14
51
  //# sourceMappingURL=types.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/gateway/types.ts"],"names":[],"mappings":";AAAA;;;;;;;;;;GAUG"}
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/gateway/types.ts"],"names":[],"mappings":";AAAA;;;;;;;;;;GAUG;;AA2DH,gCAiBC;AAGD,sCAQC;AArCD;;;;;;;;GAQG;AACH,SAAgB,UAAU,CAAC,KAAa;IACtC,MAAM,KAAK,GAAoB,EAAE,CAAC;IAClC,IAAI,IAAI,GAAG,KAAK,CAAC;IAEjB,uCAAuC;IACvC,IAAI,GAAG,IAAI,CAAC,OAAO,CAAC,iDAAiD,EAAE,CAAC,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,GAAG,EAAE,EAAE;QAC5F,KAAK,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,WAAW,EAAsB,EAAE,GAAG,EAAE,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,SAAS,EAAE,CAAC,CAAC;QACjI,OAAO,EAAE,CAAC;IACZ,CAAC,CAAC,CAAC;IAEH,+BAA+B;IAC/B,IAAI,GAAG,IAAI,CAAC,OAAO,CAAC,4CAA4C,EAAE,CAAC,EAAE,EAAE,GAAG,EAAE,GAAG,EAAE,EAAE;QACjF,KAAK,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,SAAS,EAAE,CAAC,CAAC;QAClG,OAAO,EAAE,CAAC;IACZ,CAAC,CAAC,CAAC;IAEH,OAAO,EAAE,IAAI,EAAE,IAAI,CAAC,OAAO,CAAC,SAAS,EAAE,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,KAAK,EAAE,CAAC;AACjE,CAAC;AAED,2EAA2E;AAC3E,SAAgB,aAAa,CAAC,KAAoC;IAChE,IAAI,CAAC,KAAK,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,EAAE,CAAC;IAC5C,MAAM,KAAK,GAAG,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE;QAC5B,MAAM,KAAK,GAAG,CAAC,CAAC,QAAQ,IAAI,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,GAAG,IAAI,EAAE,CAAC;QACjD,MAAM,GAAG,GAAG,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,IAAI,KAAK,KAAK,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;QACnD,OAAO,IAAI,GAAG,GAAG,CAAC;IACpB,CAAC,CAAC,CAAC;IACH,OAAO,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AACzB,CAAC"}
@@ -0,0 +1,23 @@
1
+ /**
2
+ * Vision describe — turn an inbound image into a text description so the agent
3
+ * can "see" what the user sent, without rewiring the core text-only LLM loop.
4
+ *
5
+ * Self-contained on purpose: a single OpenAI-compatible chat/completions call
6
+ * with an image_url (base64 data URL) content block. The model + key are
7
+ * resolved from config.channels.<id>.visionModel / config.llm.vision_model
8
+ * (default gpt-4o-mini), falling back to env keys the same way the rest of
9
+ * Skyloom does. If no key/model is available, vision is skipped silently and the
10
+ * gateway just uses the media description line.
11
+ */
12
+ import type { LoadedMedia } from './helpers';
13
+ export interface VisionOptions {
14
+ model?: string;
15
+ env?: NodeJS.ProcessEnv;
16
+ prompt?: string;
17
+ }
18
+ /**
19
+ * Describe one or more images. Returns a description string, or null if vision
20
+ * is unavailable (no key/model) or fails — callers fall back to the media line.
21
+ */
22
+ export declare function describeImages(images: LoadedMedia[], opts?: VisionOptions): Promise<string | null>;
23
+ //# sourceMappingURL=vision.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"vision.d.ts","sourceRoot":"","sources":["../../src/gateway/vision.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAIH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAyB7C,MAAM,WAAW,aAAa;IAC5B,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC;IACxB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED;;;GAGG;AACH,wBAAsB,cAAc,CAAC,MAAM,EAAE,WAAW,EAAE,EAAE,IAAI,GAAE,aAAkB,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CA4B5G"}
@@ -0,0 +1,77 @@
1
+ "use strict";
2
+ /**
3
+ * Vision describe — turn an inbound image into a text description so the agent
4
+ * can "see" what the user sent, without rewiring the core text-only LLM loop.
5
+ *
6
+ * Self-contained on purpose: a single OpenAI-compatible chat/completions call
7
+ * with an image_url (base64 data URL) content block. The model + key are
8
+ * resolved from config.channels.<id>.visionModel / config.llm.vision_model
9
+ * (default gpt-4o-mini), falling back to env keys the same way the rest of
10
+ * Skyloom does. If no key/model is available, vision is skipped silently and the
11
+ * gateway just uses the media description line.
12
+ */
13
+ var __importDefault = (this && this.__importDefault) || function (mod) {
14
+ return (mod && mod.__esModule) ? mod : { "default": mod };
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ exports.describeImages = describeImages;
18
+ const axios_1 = __importDefault(require("axios"));
19
+ const logger_1 = require("../core/logger");
20
+ const log = (0, logger_1.getLogger)('gateway-vision');
21
+ /** OpenAI-compatible base URL for a provider inferred from the model id. */
22
+ function baseUrlFor(model) {
23
+ const l = model.toLowerCase();
24
+ if (l.includes('claude'))
25
+ return 'https://api.anthropic.com/v1'; // not OpenAI-shaped; skipped below
26
+ if (l.includes('gemini'))
27
+ return 'https://generativelanguage.googleapis.com/v1beta/openai';
28
+ if (l.includes('grok') || l.includes('xai'))
29
+ return 'https://api.x.ai/v1';
30
+ if (l.includes('qwen') || l.includes('dashscope'))
31
+ return 'https://dashscope.aliyuncs.com/compatible-mode/v1';
32
+ return 'https://api.openai.com/v1';
33
+ }
34
+ /** Resolve an API key for the vision model from env (best-effort). */
35
+ function keyFor(model, env) {
36
+ const l = model.toLowerCase();
37
+ const candidates = l.includes('gemini') ? ['GEMINI_API_KEY', 'GOOGLE_API_KEY']
38
+ : l.includes('grok') || l.includes('xai') ? ['XAI_API_KEY']
39
+ : l.includes('qwen') || l.includes('dashscope') ? ['DASHSCOPE_API_KEY', 'QWEN_API_KEY']
40
+ : ['OPENAI_API_KEY'];
41
+ for (const c of candidates)
42
+ if (env[c])
43
+ return env[c];
44
+ return undefined;
45
+ }
46
+ /**
47
+ * Describe one or more images. Returns a description string, or null if vision
48
+ * is unavailable (no key/model) or fails — callers fall back to the media line.
49
+ */
50
+ async function describeImages(images, opts = {}) {
51
+ if (!images.length)
52
+ return null;
53
+ const env = opts.env || process.env;
54
+ const model = opts.model || 'gpt-4o-mini';
55
+ // Anthropic isn't OpenAI-chat-shaped here; skip to keep this helper simple.
56
+ if (model.toLowerCase().includes('claude'))
57
+ return null;
58
+ const key = keyFor(model, env);
59
+ if (!key)
60
+ return null;
61
+ const prompt = opts.prompt || '请用中文简洁描述这些图片的内容(关键物体、文字、场景);如果含可读文字请转写出来。';
62
+ const content = [{ type: 'text', text: prompt }];
63
+ for (const img of images.slice(0, 4)) {
64
+ const mime = img.contentType || 'image/png';
65
+ content.push({ type: 'image_url', image_url: { url: `data:${mime};base64,${img.data.toString('base64')}` } });
66
+ }
67
+ try {
68
+ const res = await axios_1.default.post(`${baseUrlFor(model)}/chat/completions`, { model, messages: [{ role: 'user', content }], max_tokens: 500, temperature: 0.2 }, { headers: { 'Content-Type': 'application/json', Authorization: `Bearer ${key}` }, timeout: 30000, validateStatus: (s) => s >= 200 && s < 300 });
69
+ const text = res.data?.choices?.[0]?.message?.content;
70
+ return typeof text === 'string' && text.trim() ? text.trim() : null;
71
+ }
72
+ catch (e) {
73
+ log.warn('vision_describe_failed', { model, error: String(e).slice(0, 160) });
74
+ return null;
75
+ }
76
+ }
77
+ //# sourceMappingURL=vision.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"vision.js","sourceRoot":"","sources":["../../src/gateway/vision.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "skyloom",
3
- "version": "1.21.0",
3
+ "version": "1.23.0",
4
4
  "description": "天空织机 Skyloom — 6 weather-themed AI agents: Fog, Rain, Frost, Snow, Dew, Fair",
5
5
  "preferGlobal": true,
6
6
  "type": "commonjs",