@antglobal/copilot-cards-mini-program 0.0.0 → 0.0.20260724033338-dev.13

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 (67) hide show
  1. package/README.md +126 -2
  2. package/dist/action-context/index.d.ts +44 -0
  3. package/dist/action-context/index.js +70 -0
  4. package/dist/adapter/alipay.d.ts +22 -0
  5. package/dist/adapter/alipay.js +65 -0
  6. package/dist/adapter/index.d.ts +53 -0
  7. package/dist/adapter/index.js +2 -0
  8. package/dist/adapter/wechat.d.ts +22 -0
  9. package/dist/adapter/wechat.js +65 -0
  10. package/dist/components/card-button/index.acss +61 -0
  11. package/dist/components/card-button/index.axml +9 -0
  12. package/dist/components/card-button/index.d.ts +23 -0
  13. package/dist/components/card-button/index.js +26 -0
  14. package/dist/components/card-button/index.wxml +9 -0
  15. package/dist/components/card-divider/index.acss +8 -0
  16. package/dist/components/card-divider/index.axml +5 -0
  17. package/dist/components/card-divider/index.d.ts +11 -0
  18. package/dist/components/card-divider/index.js +13 -0
  19. package/dist/components/card-divider/index.wxml +5 -0
  20. package/dist/components/card-icon/definition.d.ts +15 -0
  21. package/dist/components/card-icon/definition.js +17 -0
  22. package/dist/components/card-icon/index.acss +19 -0
  23. package/dist/components/card-icon/index.axml +16 -0
  24. package/dist/components/card-icon/index.d.ts +1 -0
  25. package/dist/components/card-icon/index.js +8 -0
  26. package/dist/components/card-icon/index.json +3 -0
  27. package/dist/components/card-icon/index.wxml +16 -0
  28. package/dist/components/card-icon/index.wxss +19 -0
  29. package/dist/components/card-image/index.acss +7 -0
  30. package/dist/components/card-image/index.axml +9 -0
  31. package/dist/components/card-image/index.d.ts +22 -0
  32. package/dist/components/card-image/index.js +22 -0
  33. package/dist/components/card-image/index.wxml +9 -0
  34. package/dist/components/card-input/index.acss +24 -0
  35. package/dist/components/card-input/index.axml +16 -0
  36. package/dist/components/card-input/index.d.ts +25 -0
  37. package/dist/components/card-input/index.js +45 -0
  38. package/dist/components/card-input/index.wxml +16 -0
  39. package/dist/components/card-node/index.acss +5 -0
  40. package/dist/components/card-node/index.axml +30 -0
  41. package/dist/components/card-node/index.d.ts +31 -0
  42. package/dist/components/card-node/index.js +28 -0
  43. package/dist/components/card-node/index.wxml +30 -0
  44. package/dist/components/card-root/index.acss +4 -0
  45. package/dist/components/card-root/index.axml +4 -0
  46. package/dist/components/card-root/index.d.ts +78 -0
  47. package/dist/components/card-root/index.js +93 -0
  48. package/dist/components/card-root/index.wxml +4 -0
  49. package/dist/components/card-text/index.acss +11 -0
  50. package/dist/components/card-text/index.axml +8 -0
  51. package/dist/components/card-text/index.d.ts +23 -0
  52. package/dist/components/card-text/index.js +23 -0
  53. package/dist/components/card-text/index.wxml +8 -0
  54. package/dist/events/index.d.ts +37 -0
  55. package/dist/events/index.js +50 -0
  56. package/dist/icons.d.ts +3 -0
  57. package/dist/icons.js +135 -0
  58. package/dist/index.d.ts +17 -0
  59. package/dist/index.js +16 -0
  60. package/dist/renderer/index.d.ts +67 -0
  61. package/dist/renderer/index.js +158 -0
  62. package/dist/renderer/transform.d.ts +24 -0
  63. package/dist/renderer/transform.js +91 -0
  64. package/dist/streaming/index.d.ts +80 -0
  65. package/dist/streaming/index.js +230 -0
  66. package/package.json +38 -7
  67. package/LEGAL.md +0 -7
@@ -0,0 +1,80 @@
1
+ import { StreamingCommand, ExpressionContext, StreamingParserOptions } from '@antglobal/copilot-cards-core';
2
+ import { MiniProgramRenderNode } from '../renderer/index.js';
3
+ import { MiniProgramAdapter } from '../adapter/index.js';
4
+
5
+ /**
6
+ * Streaming Adapter for Mini-Program — enables progressive card rendering
7
+ * in WeChat/Alipay/DingTalk mini-programs via streaming commands.
8
+ *
9
+ * Since mini-programs cannot directly manipulate DOM, this module
10
+ * produces incremental setData patches that the framework can apply efficiently.
11
+ *
12
+ * Key differences from Web streaming:
13
+ * - Returns data patches instead of manipulating DOM
14
+ * - Uses path-based setData for efficient mini-program updates
15
+ * - Computes minimal diff for appendContent operations
16
+ */
17
+
18
+ interface MiniProgramStreamingOptions {
19
+ /** Platform adapter instance */
20
+ adapter: MiniProgramAdapter;
21
+ /** Initial variables data context */
22
+ data?: ExpressionContext;
23
+ /** Bot ID for bot-scoped action handlers */
24
+ botId?: string;
25
+ /** Event emitter — called when an emit action fires */
26
+ onEmit?: (eventName: string, payload?: unknown) => void;
27
+ /** Parser options */
28
+ parserOptions?: StreamingParserOptions;
29
+ }
30
+ /**
31
+ * Represents a data patch that should be applied via mini-program's setData.
32
+ */
33
+ interface DataPatch {
34
+ /** The path-value pairs for setData, e.g. { 'tree.children[0].props.content': 'new text' } */
35
+ data: Record<string, any>;
36
+ }
37
+ interface MiniProgramStreamingCardInstance {
38
+ /** Apply a single streaming command, returns setData patch or null */
39
+ applyCommand(command: StreamingCommand): DataPatch | null;
40
+ /** Apply multiple commands, returns array of patches */
41
+ applyCommands(commands: StreamingCommand[]): DataPatch[];
42
+ /** Feed raw text chunk, returns array of patches */
43
+ feed(chunk: string): DataPatch[];
44
+ /** Flush parser buffer, returns remaining patches */
45
+ flush(): DataPatch[];
46
+ /** Get current full render data */
47
+ getData(): {
48
+ tree: MiniProgramRenderNode | null;
49
+ };
50
+ /** Handle a component event */
51
+ handleEvent(nodeId: string, eventName: string, eventDetail?: any): Promise<DataPatch | null>;
52
+ /** Dispose the instance */
53
+ dispose(): void;
54
+ }
55
+ /**
56
+ * Create a mini-program streaming card instance.
57
+ *
58
+ * Unlike the web streaming renderer which directly updates DOM,
59
+ * this returns data patches that should be applied via the
60
+ * mini-program framework's setData mechanism.
61
+ *
62
+ * @example
63
+ * ```ts
64
+ * // In mini-program component
65
+ * const streaming = createStreamingCardInstance({
66
+ * adapter: new AlipayAdapter(),
67
+ * data: { userName: 'Alice' },
68
+ * });
69
+ *
70
+ * // Feed streaming data (e.g. from WebSocket)
71
+ * socket.onmessage = (e) => {
72
+ * const patches = streaming.feed(e.data);
73
+ * patches.forEach(patch => this.setData(patch.data));
74
+ * };
75
+ * ```
76
+ */
77
+ declare function createStreamingCardInstance(options: MiniProgramStreamingOptions): MiniProgramStreamingCardInstance;
78
+
79
+ export { createStreamingCardInstance };
80
+ export type { DataPatch, MiniProgramStreamingCardInstance, MiniProgramStreamingOptions };
@@ -0,0 +1,230 @@
1
+ import { StreamingParser, StreamingEngine, normalizeSchema } from '@antglobal/copilot-cards-core';
2
+ import { renderForMiniProgram } from '../renderer/index.js';
3
+
4
+ /**
5
+ * Streaming Adapter for Mini-Program — enables progressive card rendering
6
+ * in WeChat/Alipay/DingTalk mini-programs via streaming commands.
7
+ *
8
+ * Since mini-programs cannot directly manipulate DOM, this module
9
+ * produces incremental setData patches that the framework can apply efficiently.
10
+ *
11
+ * Key differences from Web streaming:
12
+ * - Returns data patches instead of manipulating DOM
13
+ * - Uses path-based setData for efficient mini-program updates
14
+ * - Computes minimal diff for appendContent operations
15
+ */
16
+ // ─── Main API ────────────────────────────────────────────────────
17
+ /**
18
+ * Create a mini-program streaming card instance.
19
+ *
20
+ * Unlike the web streaming renderer which directly updates DOM,
21
+ * this returns data patches that should be applied via the
22
+ * mini-program framework's setData mechanism.
23
+ *
24
+ * @example
25
+ * ```ts
26
+ * // In mini-program component
27
+ * const streaming = createStreamingCardInstance({
28
+ * adapter: new AlipayAdapter(),
29
+ * data: { userName: 'Alice' },
30
+ * });
31
+ *
32
+ * // Feed streaming data (e.g. from WebSocket)
33
+ * socket.onmessage = (e) => {
34
+ * const patches = streaming.feed(e.data);
35
+ * patches.forEach(patch => this.setData(patch.data));
36
+ * };
37
+ * ```
38
+ */
39
+ function createStreamingCardInstance(options) {
40
+ const parser = new StreamingParser(options.parserOptions);
41
+ let currentInstance = null;
42
+ let currentTree = null;
43
+ let variables = { ...options.data };
44
+ // Track node paths for efficient patching
45
+ const nodePathMap = new Map(); // elementId → setData path
46
+ /**
47
+ * Build the node path map by traversing the tree.
48
+ */
49
+ function buildNodePaths(node, basePath) {
50
+ nodePathMap.set(node.id, basePath);
51
+ node.children.forEach((child, index) => {
52
+ buildNodePaths(child, `${basePath}.children[${index}]`);
53
+ });
54
+ }
55
+ /**
56
+ * Create a full tree patch (for initial render or full re-render).
57
+ */
58
+ function createFullPatch() {
59
+ return { data: { tree: currentTree } };
60
+ }
61
+ // ─── Engine Setup ───────────────────────────────────────────────
62
+ const pendingPatches = [];
63
+ const engine = new StreamingEngine({
64
+ onSurfaceCreated(surfaceId, schemaInput) {
65
+ if (schemaInput) {
66
+ const schema = normalizeSchema(schemaInput);
67
+ variables = { ...schema.variables, ...options.data };
68
+ currentInstance = renderForMiniProgram(schema, {
69
+ adapter: options.adapter,
70
+ data: variables,
71
+ botId: options.botId,
72
+ onEmit: options.onEmit,
73
+ });
74
+ currentTree = currentInstance.getData().tree;
75
+ if (currentTree) {
76
+ nodePathMap.clear();
77
+ buildNodePaths(currentTree, 'tree');
78
+ }
79
+ pendingPatches.push(createFullPatch());
80
+ }
81
+ },
82
+ onComponentsUpdated(surfaceId, changes) {
83
+ // For mini-program, component tree changes require full re-render
84
+ // because we can't insert DOM nodes — we need to regenerate the data tree
85
+ const schema = engine.getSchema(surfaceId);
86
+ if (!schema)
87
+ return;
88
+ currentInstance = renderForMiniProgram(schema, {
89
+ adapter: options.adapter,
90
+ data: variables,
91
+ botId: options.botId,
92
+ onEmit: options.onEmit,
93
+ });
94
+ currentTree = currentInstance.getData().tree;
95
+ if (currentTree) {
96
+ nodePathMap.clear();
97
+ buildNodePaths(currentTree, 'tree');
98
+ }
99
+ pendingPatches.push(createFullPatch());
100
+ },
101
+ onDataModelUpdated(surfaceId, path, value) {
102
+ if (!currentInstance)
103
+ return;
104
+ // Update variables and regenerate tree
105
+ const pathParts = path.replace(/^\//, '').split('/').filter(Boolean);
106
+ if (pathParts.length === 0) {
107
+ if (typeof value === 'object' && value !== null) {
108
+ variables = { ...variables, ...value };
109
+ }
110
+ }
111
+ else {
112
+ let current = variables;
113
+ for (let i = 0; i < pathParts.length - 1; i++) {
114
+ if (current[pathParts[i]] === undefined)
115
+ current[pathParts[i]] = {};
116
+ current = current[pathParts[i]];
117
+ }
118
+ current[pathParts[pathParts.length - 1]] = value;
119
+ }
120
+ const result = currentInstance.updateVariables(variables);
121
+ currentTree = result.tree;
122
+ if (currentTree) {
123
+ nodePathMap.clear();
124
+ buildNodePaths(currentTree, 'tree');
125
+ }
126
+ pendingPatches.push(createFullPatch());
127
+ },
128
+ onContentAppended(surfaceId, elementId, content) {
129
+ // Try to do a targeted patch for text content
130
+ const nodePath = nodePathMap.get(elementId);
131
+ if (nodePath && currentTree) {
132
+ // Find the node and update its content in-place
133
+ const node = findNodeById(currentTree, elementId);
134
+ if (node) {
135
+ const currentContent = typeof node.props.content === 'string'
136
+ ? node.props.content : '';
137
+ node.props.content = currentContent + content;
138
+ // Generate a path-based setData patch for efficiency
139
+ pendingPatches.push({
140
+ data: { [`${nodePath}.props.content`]: node.props.content },
141
+ });
142
+ return;
143
+ }
144
+ }
145
+ // Fallback: full re-render
146
+ if (currentInstance) {
147
+ const schema = engine.getSchema(surfaceId);
148
+ if (schema) {
149
+ variables = { ...schema.variables, ...variables };
150
+ const result = currentInstance.updateVariables(variables);
151
+ currentTree = result.tree;
152
+ pendingPatches.push(createFullPatch());
153
+ }
154
+ }
155
+ },
156
+ onSurfaceDeleted(surfaceId) {
157
+ currentInstance?.dispose();
158
+ currentInstance = null;
159
+ currentTree = null;
160
+ nodePathMap.clear();
161
+ pendingPatches.push({ data: { tree: null } });
162
+ },
163
+ });
164
+ // ─── Helpers ────────────────────────────────────────────────────
165
+ function findNodeById(node, id) {
166
+ if (node.id === id)
167
+ return node;
168
+ for (const child of node.children) {
169
+ const found = findNodeById(child, id);
170
+ if (found)
171
+ return found;
172
+ }
173
+ return null;
174
+ }
175
+ function drainPatches() {
176
+ const patches = [...pendingPatches];
177
+ pendingPatches.length = 0;
178
+ return patches;
179
+ }
180
+ // ─── Public API ─────────────────────────────────────────────────
181
+ return {
182
+ applyCommand(command) {
183
+ engine.apply(command);
184
+ const patches = drainPatches();
185
+ return patches.length > 0 ? patches[patches.length - 1] : null;
186
+ },
187
+ applyCommands(commands) {
188
+ engine.applyBatch(commands);
189
+ return drainPatches();
190
+ },
191
+ feed(chunk) {
192
+ const commands = parser.parse(chunk);
193
+ for (const cmd of commands) {
194
+ engine.apply(cmd);
195
+ }
196
+ return drainPatches();
197
+ },
198
+ flush() {
199
+ const commands = parser.flush();
200
+ for (const cmd of commands) {
201
+ engine.apply(cmd);
202
+ }
203
+ return drainPatches();
204
+ },
205
+ getData() {
206
+ return { tree: currentTree };
207
+ },
208
+ async handleEvent(nodeId, eventName, eventDetail) {
209
+ if (!currentInstance)
210
+ return null;
211
+ await currentInstance.handleEvent(nodeId, eventName, eventDetail);
212
+ currentTree = currentInstance.getData().tree;
213
+ if (currentTree) {
214
+ nodePathMap.clear();
215
+ buildNodePaths(currentTree, 'tree');
216
+ }
217
+ return createFullPatch();
218
+ },
219
+ dispose() {
220
+ currentInstance?.dispose();
221
+ currentInstance = null;
222
+ currentTree = null;
223
+ nodePathMap.clear();
224
+ engine.dispose();
225
+ parser.reset();
226
+ },
227
+ };
228
+ }
229
+
230
+ export { createStreamingCardInstance };
package/package.json CHANGED
@@ -1,12 +1,43 @@
1
1
  {
2
2
  "name": "@antglobal/copilot-cards-mini-program",
3
- "version": "0.0.0",
4
- "description": "",
5
- "main": "index.js",
3
+ "version": "0.0.20260724033338-dev.13",
4
+ "description": "Mini-program native renderer for copilot bot card SDK — adapts to WeChat / Alipay / DingTalk mini-program templates",
5
+ "type": "module",
6
+ "module": "./dist/index.js",
7
+ "types": "./dist/index.d.ts",
8
+ "exports": {
9
+ ".": {
10
+ "types": "./dist/index.d.ts",
11
+ "import": "./dist/index.js",
12
+ "default": "./dist/index.js"
13
+ }
14
+ },
15
+ "miniprogram": "dist",
16
+ "files": [
17
+ "dist"
18
+ ],
6
19
  "scripts": {
7
- "test": "echo \"Error: no test specified\" && exit 1"
20
+ "clean": "node -e \"require('node:fs').rmSync('dist', { recursive: true, force: true })\"",
21
+ "build": "npm run clean && tsc -p ../copilot-cards-mini-program/tsconfig.json --noEmit && rollup -c && node scripts/postbuild.mjs"
22
+ },
23
+ "keywords": [
24
+ "copilot",
25
+ "bot",
26
+ "card",
27
+ "mini-program",
28
+ "wechat",
29
+ "alipay"
30
+ ],
31
+ "license": "MIT",
32
+ "dependencies": {
33
+ "@antglobal/copilot-cards-core": "0.0.20260724033338-dev.13",
34
+ "tslib": "^2.8.1"
35
+ },
36
+ "devDependencies": {
37
+ "@types/node": "^20",
38
+ "rollup": "^4.9.0",
39
+ "rollup-plugin-dts": "^6.1.0",
40
+ "typescript": "^5.3.0"
8
41
  },
9
- "keywords": [],
10
- "author": "",
11
- "license": "MIT"
42
+ "marmotId": "180020050100014006"
12
43
  }
package/LEGAL.md DELETED
@@ -1,7 +0,0 @@
1
- Legal Disclaimer
2
-
3
- Within this source code, the comments in Chinese shall be the original, governing version. Any comment in other languages are for reference only. In the event of any conflict between the Chinese language version comments and other language version comments, the Chinese language version shall prevail.
4
-
5
- 法律免责声明
6
-
7
- 关于代码注释部分,中文注释为官方版本,其它语言注释仅做参考。中文注释可能与其它语言注释存在不一致,当中文注释与其它语言注释存在不一致时,请以中文注释为准。