@rinova/playground-mcp 0.1.5 → 0.5.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 (3) hide show
  1. package/README.md +1 -1
  2. package/dist/index.js +42 -10
  3. package/package.json +1 -1
package/README.md CHANGED
@@ -46,7 +46,7 @@ export default defineConfig({
46
46
 
47
47
  ## 工具
48
48
 
49
- | 工具 | 入参 | 返回 |
49
+ | 工具 | 输入 | 返回 |
50
50
  |---|---|---|
51
51
  | `capability_search` | `query`、`limit?` | 命中的组件 + prop 名 + 场景数 |
52
52
  | `capability_get` | `component` | props/events/slots/exposed 全量契约,每个 prop 带 `文件:行号`,附相关场景与未覆盖 props |
package/dist/index.js CHANGED
@@ -11,9 +11,15 @@ const locate = (root, rel, needle) => {
11
11
  if (!fs.existsSync(abs))
12
12
  return rel;
13
13
  const lines = fs.readFileSync(abs, 'utf8').split('\n');
14
- const pattern = new RegExp(`\\b${needle.replace(/[.*+?^${}()|[\]\\]/g, '\\$&')}\\b`);
15
- const index = lines.findIndex((line) => pattern.test(line));
16
- return index >= 0 ? `${rel}:${index + 1}` : rel;
14
+ const escaped = needle.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
15
+ // 先找声明行(`rows?:` / `rows:` / `rows =`),避免命中 JSDoc 里提到的同名词
16
+ const declaration = new RegExp(`^\\s*(?:readonly\\s+)?${escaped}\\??\\s*[:=]`);
17
+ const word = new RegExp(`\\b${escaped}\\b`);
18
+ const isComment = (line) => /^\s*(?:\*|\/\/|<!--)/.test(line);
19
+ const codeLines = lines.map((line, index) => ({ line, index })).filter((item) => !isComment(item.line));
20
+ const hit = codeLines.find((item) => declaration.test(item.line)) ??
21
+ codeLines.find((item) => word.test(item.line));
22
+ return hit ? `${rel}:${hit.index + 1}` : rel;
17
23
  };
18
24
  const parseArgs = (argv) => {
19
25
  const args = argv.slice(2);
@@ -47,13 +53,39 @@ const formatComponent = (root, component, manifest) => {
47
53
  lines.push(`- ${prop.name}: ${prop.type}${flags ? ` (${flags})` : ''} ← ${locate(root, component.rel, prop.name)}`);
48
54
  if (prop.description)
49
55
  lines.push(` ${prop.description}`);
56
+ for (const field of prop.fields ?? []) {
57
+ lines.push(` · ${field.name}: ${field.type}${field.required ? ' (必填)' : ''}${field.description ? ` — ${field.description}` : ''}`);
58
+ }
59
+ }
60
+ if (component.events.length) {
61
+ lines.push('', '## Events');
62
+ for (const event of component.events) {
63
+ lines.push(`- ${event.name} ${event.type}${event.description ? ` — ${event.description}` : ''}`);
64
+ if (event.signature)
65
+ lines.push(` ${event.signature}`);
66
+ for (const field of event.fields ?? []) {
67
+ lines.push(` · ${field.name}: ${field.type}${field.description ? ` — ${field.description}` : ''}`);
68
+ }
69
+ }
70
+ }
71
+ if (component.slots.length) {
72
+ lines.push('', '## Slots');
73
+ for (const slot of component.slots) {
74
+ lines.push(`- ${slot.name}${slot.description ? ` — ${slot.description}` : ''}`);
75
+ }
76
+ }
77
+ if (component.exposed.length) {
78
+ lines.push('', '## Exposed');
79
+ for (const item of component.exposed) {
80
+ lines.push(`- ${item.name}: ${item.type}${item.description ? ` — ${item.description}` : ''}`);
81
+ }
82
+ }
83
+ if (component.types?.length) {
84
+ lines.push('', '## Types');
85
+ for (const item of component.types) {
86
+ lines.push(`- ${item.name}(${item.kind},${item.file})`, '```ts', item.code, '```');
87
+ }
50
88
  }
51
- if (component.events.length)
52
- lines.push('', `## Events`, ...component.events.map((name) => `- ${name}`));
53
- if (component.slots.length)
54
- lines.push('', `## Slots`, ...component.slots.map((name) => `- ${name}`));
55
- if (component.exposed.length)
56
- lines.push('', `## Exposed`, ...component.exposed.map((name) => `- ${name}`));
57
89
  const scenes = manifest.scenes.filter((scene) => component.scenes.includes(scene.id));
58
90
  lines.push('', '## 相关场景');
59
91
  if (!scenes.length)
@@ -84,7 +116,7 @@ const main = async () => {
84
116
  process.exitCode = 1;
85
117
  return;
86
118
  }
87
- const server = new McpServer({ name: 'rinova-playground', version: '0.1.0' });
119
+ const server = new McpServer({ name: 'rinova-playground', version: '0.5.0' });
88
120
  server.registerTool('capability_search', {
89
121
  title: '搜索组件能力',
90
122
  description: '按组件名 / prop 名 / 场景 id 搜索,返回带文件行号的摘要',
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rinova/playground-mcp",
3
- "version": "0.1.5",
3
+ "version": "0.5.0",
4
4
  "description": "rinova-playground 的 MCP server:把契约清单暴露给 AI 编码工具",
5
5
  "type": "module",
6
6
  "license": "MIT",