tkeron 5.2.0 → 6.0.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.
- package/README.md +17 -16
- package/bun.lock +13 -196
- package/changelog.md +52 -3
- package/examples/init_sample/websrc/api-service.ts +24 -24
- package/examples/init_sample/websrc/counter-card.com.html +5 -2
- package/examples/init_sample/websrc/hero-section.com.html +35 -5
- package/examples/init_sample/websrc/html-components-card.com.html +6 -2
- package/examples/init_sample/websrc/index.html +58 -25
- package/examples/init_sample/websrc/index.pre.ts +20 -15
- package/examples/init_sample/websrc/ts-components-card.com.html +7 -2
- package/examples/with_style_dedup/websrc/index.html +29 -0
- package/examples/with_style_dedup/websrc/tag-chip.com.ts +19 -0
- package/index.ts +15 -0
- package/package.json +10 -23
- package/skills/tkeron/SKILL.md +286 -0
- package/skills/tkeron-components/SKILL.md +785 -0
- package/skills/tkeron-organization/SKILL.md +230 -0
- package/skills/tkeron-patterns/SKILL.md +495 -0
- package/skills/tkeron-testing/SKILL.md +194 -0
- package/skills/tkeron-troubleshooting/SKILL.md +259 -0
- package/src/build.ts +7 -6
- package/src/deduplicateComStyles.ts +41 -0
- package/src/develop.ts +1 -2
- package/src/init.ts +1 -2
- package/src/processCom.ts +2 -2
- package/src/processComTs.ts +2 -2
- package/src/skills.ts +139 -0
- package/src/skillsWrapper.ts +79 -0
- package/docs/mcp-server.md +0 -240
- package/mcp-server.ts +0 -272
- package/src/cleanupOrphanedTempDirs.ts +0 -31
- package/src/promptUser.ts +0 -15
- package/src/setupSigintHandler.ts +0 -6
package/docs/mcp-server.md
DELETED
|
@@ -1,240 +0,0 @@
|
|
|
1
|
-
# MCP Server
|
|
2
|
-
|
|
3
|
-
Tkeron includes a Model Context Protocol (MCP) server that exposes comprehensive documentation to AI agents and development tools.
|
|
4
|
-
|
|
5
|
-
## What is MCP?
|
|
6
|
-
|
|
7
|
-
The Model Context Protocol is a standard for providing context to AI agents. Tkeron's MCP server allows AI assistants to access up-to-date documentation about how to use Tkeron, its capabilities, and limitations.
|
|
8
|
-
|
|
9
|
-
## Installation
|
|
10
|
-
|
|
11
|
-
The MCP server is included when you install Tkeron globally:
|
|
12
|
-
|
|
13
|
-
```bash
|
|
14
|
-
bun install -g tkeron
|
|
15
|
-
```
|
|
16
|
-
|
|
17
|
-
This installs three commands:
|
|
18
|
-
|
|
19
|
-
- `tk` / `tkeron` - The main CLI tool
|
|
20
|
-
- `tkeron-mcp` - The MCP server
|
|
21
|
-
|
|
22
|
-
## Configuration
|
|
23
|
-
|
|
24
|
-
### VS Code
|
|
25
|
-
|
|
26
|
-
Add to your MCP configuration file (`~/.config/Code/User/mcp.json`):
|
|
27
|
-
|
|
28
|
-
```json
|
|
29
|
-
{
|
|
30
|
-
"servers": {
|
|
31
|
-
"tkeron": {
|
|
32
|
-
"command": "tkeron-mcp"
|
|
33
|
-
}
|
|
34
|
-
}
|
|
35
|
-
}
|
|
36
|
-
```
|
|
37
|
-
|
|
38
|
-
If the global command is not found, use Bun directly:
|
|
39
|
-
|
|
40
|
-
```json
|
|
41
|
-
{
|
|
42
|
-
"servers": {
|
|
43
|
-
"tkeron": {
|
|
44
|
-
"command": "bun",
|
|
45
|
-
"args": ["run", "/absolute/path/to/tkeron/mcp-server.ts"]
|
|
46
|
-
}
|
|
47
|
-
}
|
|
48
|
-
}
|
|
49
|
-
```
|
|
50
|
-
|
|
51
|
-
**Note:** This is the VS Code format. Other editors (Cursor, Windsurf, etc.) may use different configuration formats.
|
|
52
|
-
|
|
53
|
-
````
|
|
54
|
-
|
|
55
|
-
**Find the path:**
|
|
56
|
-
```bash
|
|
57
|
-
# If tkeron is installed globally
|
|
58
|
-
dirname $(which tk)
|
|
59
|
-
# Returns something like: /home/user/.bun/bin
|
|
60
|
-
|
|
61
|
-
# The mcp-server.ts is in the same directory
|
|
62
|
-
ls $(dirname $(which tk))/mcp-server.ts
|
|
63
|
-
````
|
|
64
|
-
|
|
65
|
-
### Claude Desktop
|
|
66
|
-
|
|
67
|
-
Add to `~/Library/Application Support/Claude/claude_desktop_config.json` (macOS) or equivalent on other platforms:
|
|
68
|
-
|
|
69
|
-
```json
|
|
70
|
-
{
|
|
71
|
-
"mcpServers": {
|
|
72
|
-
"tkeron": {
|
|
73
|
-
"command": "tkeron-mcp"
|
|
74
|
-
}
|
|
75
|
-
}
|
|
76
|
-
}
|
|
77
|
-
```
|
|
78
|
-
|
|
79
|
-
### Other MCP Clients
|
|
80
|
-
|
|
81
|
-
Any MCP-compatible client can use the server. Configure it to run:
|
|
82
|
-
|
|
83
|
-
```bash
|
|
84
|
-
tkeron-mcp
|
|
85
|
-
```
|
|
86
|
-
|
|
87
|
-
The server communicates via stdio transport.
|
|
88
|
-
|
|
89
|
-
## Available Resources
|
|
90
|
-
|
|
91
|
-
The MCP server exposes the following documentation resources:
|
|
92
|
-
|
|
93
|
-
| URI | Description |
|
|
94
|
-
| -------------------------------- | ---------------------------------------------------- |
|
|
95
|
-
| `tkeron://overview` | What Tkeron is, what it does, and what it's not |
|
|
96
|
-
| `tkeron://getting-started` | Installation, first project, and basic workflow |
|
|
97
|
-
| `tkeron://components-html` | Create reusable HTML components with .com.html files |
|
|
98
|
-
| `tkeron://components-typescript` | Build dynamic components with .com.ts files |
|
|
99
|
-
| `tkeron://pre-rendering` | Transform HTML at build time with .pre.ts files |
|
|
100
|
-
| `tkeron://cli-reference` | Complete command-line interface documentation |
|
|
101
|
-
| `tkeron://best-practices` | Patterns, anti-patterns, and limitations |
|
|
102
|
-
| `tkeron://common-issues` | Troubleshooting guide and common mistakes |
|
|
103
|
-
| `tkeron://testing` | How to test tkeron projects with getBuildResult() |
|
|
104
|
-
|
|
105
|
-
## What AI Agents Can Do
|
|
106
|
-
|
|
107
|
-
With access to the MCP server, AI agents can:
|
|
108
|
-
|
|
109
|
-
- ✅ Understand Tkeron's capabilities and limitations
|
|
110
|
-
- ✅ Help users create components correctly
|
|
111
|
-
- ✅ Suggest appropriate patterns for different use cases
|
|
112
|
-
- ✅ Identify when Tkeron is NOT the right tool
|
|
113
|
-
- ✅ Provide accurate CLI commands and options
|
|
114
|
-
- ✅ Debug common issues with components and pre-rendering
|
|
115
|
-
- ✅ Recommend best practices and avoid anti-patterns
|
|
116
|
-
- ✅ **Prevent common mistakes** (script references, component naming, dependencies)
|
|
117
|
-
- ✅ **List and explore example projects**
|
|
118
|
-
- ✅ **Retrieve example code and structures**
|
|
119
|
-
- ✅ **Initialize, build, and develop projects via terminal** (`tk init`, `tk build`, `tk dev`)
|
|
120
|
-
|
|
121
|
-
## Available Tools
|
|
122
|
-
|
|
123
|
-
The MCP server provides the following tools for AI agents:
|
|
124
|
-
|
|
125
|
-
### Example Management Tools
|
|
126
|
-
|
|
127
|
-
- **`list_examples`**: List all available Tkeron example projects
|
|
128
|
-
- No parameters required
|
|
129
|
-
- Returns example names, descriptions, and paths
|
|
130
|
-
- Helps users discover what's possible with Tkeron
|
|
131
|
-
|
|
132
|
-
- **`get_example`**: Get the complete source code of an example
|
|
133
|
-
- Parameters: `example` (name of the example project)
|
|
134
|
-
- Returns file structure and all source code
|
|
135
|
-
- Useful for learning patterns and bootstrapping projects
|
|
136
|
-
|
|
137
|
-
> **Note:** The MCP server only provides documentation and examples. It does NOT modify files. The AI agent should use terminal commands (`tk init`, `tk build`, `tk dev`) to manage projects.
|
|
138
|
-
|
|
139
|
-
## Benefits
|
|
140
|
-
|
|
141
|
-
### For Users
|
|
142
|
-
|
|
143
|
-
- Get accurate help from AI assistants
|
|
144
|
-
- AI understands your project structure
|
|
145
|
-
- Contextual suggestions based on Tkeron's docs
|
|
146
|
-
- Fewer mistakes and faster development
|
|
147
|
-
|
|
148
|
-
### For AI Agents
|
|
149
|
-
|
|
150
|
-
- Access to authoritative, up-to-date documentation
|
|
151
|
-
- Clear understanding of limitations and constraints
|
|
152
|
-
- Examples and patterns to reference
|
|
153
|
-
- Ability to distinguish between what Tkeron can and can't do
|
|
154
|
-
|
|
155
|
-
## Verification
|
|
156
|
-
|
|
157
|
-
To verify the MCP server is working:
|
|
158
|
-
|
|
159
|
-
1. Install Tkeron globally
|
|
160
|
-
2. Configure your MCP client
|
|
161
|
-
3. Restart your IDE/editor
|
|
162
|
-
4. Ask your AI assistant: "What is Tkeron?"
|
|
163
|
-
|
|
164
|
-
The assistant should be able to provide an accurate description based on the documentation.
|
|
165
|
-
|
|
166
|
-
## Troubleshooting
|
|
167
|
-
|
|
168
|
-
### "Command not found: tkeron-mcp"
|
|
169
|
-
|
|
170
|
-
Make sure Tkeron is installed globally:
|
|
171
|
-
|
|
172
|
-
```bash
|
|
173
|
-
bun install -g tkeron
|
|
174
|
-
which tkeron-mcp
|
|
175
|
-
```
|
|
176
|
-
|
|
177
|
-
### "Cannot find module"
|
|
178
|
-
|
|
179
|
-
Ensure all dependencies are installed:
|
|
180
|
-
|
|
181
|
-
```bash
|
|
182
|
-
cd $(dirname $(which tkeron-mcp))
|
|
183
|
-
bun install
|
|
184
|
-
```
|
|
185
|
-
|
|
186
|
-
### MCP Client Not Connecting
|
|
187
|
-
|
|
188
|
-
Check your configuration file syntax:
|
|
189
|
-
|
|
190
|
-
- Valid JSON
|
|
191
|
-
- Correct command path
|
|
192
|
-
- Proper permissions on the executable
|
|
193
|
-
|
|
194
|
-
### Resources Not Loading
|
|
195
|
-
|
|
196
|
-
Verify the docs directory exists:
|
|
197
|
-
|
|
198
|
-
```bash
|
|
199
|
-
ls $(dirname $(which tkeron-mcp))/docs/
|
|
200
|
-
```
|
|
201
|
-
|
|
202
|
-
All markdown files should be present.
|
|
203
|
-
|
|
204
|
-
## For Developers
|
|
205
|
-
|
|
206
|
-
### Adding New Resources
|
|
207
|
-
|
|
208
|
-
To add new documentation resources:
|
|
209
|
-
|
|
210
|
-
1. Create a new `.md` file in `docs/`
|
|
211
|
-
2. Add an entry to the `DOCS` array in `mcp-server.ts`:
|
|
212
|
-
|
|
213
|
-
```typescript
|
|
214
|
-
{
|
|
215
|
-
uri: "tkeron://new-topic",
|
|
216
|
-
name: "New Topic",
|
|
217
|
-
description: "Description of the topic",
|
|
218
|
-
file: "new-topic.md",
|
|
219
|
-
}
|
|
220
|
-
```
|
|
221
|
-
|
|
222
|
-
3. Rebuild and publish the package
|
|
223
|
-
|
|
224
|
-
### Testing Locally
|
|
225
|
-
|
|
226
|
-
Run the MCP server directly:
|
|
227
|
-
|
|
228
|
-
```bash
|
|
229
|
-
bun run mcp-server.ts
|
|
230
|
-
```
|
|
231
|
-
|
|
232
|
-
It will wait for stdio input (this is normal for MCP servers).
|
|
233
|
-
|
|
234
|
-
Test with an MCP client or use the MCP inspector tool.
|
|
235
|
-
|
|
236
|
-
## Related Documentation
|
|
237
|
-
|
|
238
|
-
- [Overview](./overview.md) - Learn what Tkeron is
|
|
239
|
-
- [Getting Started](./getting-started.md) - Start using Tkeron
|
|
240
|
-
- [Best Practices](./best-practices.md) - Patterns and anti-patterns
|
package/mcp-server.ts
DELETED
|
@@ -1,272 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env bun
|
|
2
|
-
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
|
|
3
|
-
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
|
|
4
|
-
import { readFileSync, existsSync, readdirSync, statSync } from "fs";
|
|
5
|
-
import { join, dirname } from "path";
|
|
6
|
-
import { fileURLToPath } from "url";
|
|
7
|
-
|
|
8
|
-
const getBaseDir = () => {
|
|
9
|
-
if (import.meta.dir) {
|
|
10
|
-
return import.meta.dir;
|
|
11
|
-
}
|
|
12
|
-
const currentFile = import.meta.url
|
|
13
|
-
? fileURLToPath(import.meta.url)
|
|
14
|
-
: __filename;
|
|
15
|
-
return dirname(currentFile);
|
|
16
|
-
};
|
|
17
|
-
|
|
18
|
-
const BASE_DIR = getBaseDir();
|
|
19
|
-
const DOCS_DIR = join(BASE_DIR, "docs");
|
|
20
|
-
const EXAMPLES_DIR = join(BASE_DIR, "examples");
|
|
21
|
-
|
|
22
|
-
const getVersion = (): string => {
|
|
23
|
-
const pkgPath = join(BASE_DIR, "package.json");
|
|
24
|
-
if (existsSync(pkgPath)) {
|
|
25
|
-
const pkg = JSON.parse(readFileSync(pkgPath, "utf-8"));
|
|
26
|
-
return pkg.version || "0.0.0";
|
|
27
|
-
}
|
|
28
|
-
return "0.0.0";
|
|
29
|
-
};
|
|
30
|
-
|
|
31
|
-
const DOCS = [
|
|
32
|
-
{
|
|
33
|
-
uri: "tkeron://overview",
|
|
34
|
-
name: "Tkeron Overview",
|
|
35
|
-
description: "What tkeron is, what it does, and what it's not",
|
|
36
|
-
file: "overview.md",
|
|
37
|
-
},
|
|
38
|
-
{
|
|
39
|
-
uri: "tkeron://getting-started",
|
|
40
|
-
name: "Getting Started",
|
|
41
|
-
description: "Installation, first project, and basic workflow",
|
|
42
|
-
file: "getting-started.md",
|
|
43
|
-
},
|
|
44
|
-
{
|
|
45
|
-
uri: "tkeron://components-html",
|
|
46
|
-
name: "HTML Components",
|
|
47
|
-
description: "Create reusable HTML components with .com.html files",
|
|
48
|
-
file: "components-html.md",
|
|
49
|
-
},
|
|
50
|
-
{
|
|
51
|
-
uri: "tkeron://components-typescript",
|
|
52
|
-
name: "TypeScript Components",
|
|
53
|
-
description: "Build dynamic components with .com.ts files",
|
|
54
|
-
file: "components-typescript.md",
|
|
55
|
-
},
|
|
56
|
-
{
|
|
57
|
-
uri: "tkeron://components-markdown",
|
|
58
|
-
name: "Markdown Components",
|
|
59
|
-
description: "Create components with Markdown using .com.md files",
|
|
60
|
-
file: "components-markdown.md",
|
|
61
|
-
},
|
|
62
|
-
{
|
|
63
|
-
uri: "tkeron://pre-rendering",
|
|
64
|
-
name: "Pre-rendering",
|
|
65
|
-
description: "Transform HTML at build time with .pre.ts files",
|
|
66
|
-
file: "pre-rendering.md",
|
|
67
|
-
},
|
|
68
|
-
{
|
|
69
|
-
uri: "tkeron://cli-reference",
|
|
70
|
-
name: "CLI Reference",
|
|
71
|
-
description: "Complete command-line interface documentation",
|
|
72
|
-
file: "cli-reference.md",
|
|
73
|
-
},
|
|
74
|
-
{
|
|
75
|
-
uri: "tkeron://best-practices",
|
|
76
|
-
name: "Best Practices",
|
|
77
|
-
description: "Patterns, anti-patterns, and limitations",
|
|
78
|
-
file: "best-practices.md",
|
|
79
|
-
},
|
|
80
|
-
{
|
|
81
|
-
uri: "tkeron://common-issues",
|
|
82
|
-
name: "Common Issues and Solutions",
|
|
83
|
-
description:
|
|
84
|
-
"Troubleshooting guide: script references, component naming, dependencies, and common mistakes",
|
|
85
|
-
file: "common-issues.md",
|
|
86
|
-
},
|
|
87
|
-
{
|
|
88
|
-
uri: "tkeron://testing",
|
|
89
|
-
name: "Testing Tkeron Projects",
|
|
90
|
-
description:
|
|
91
|
-
"How to test tkeron projects using getBuildResult(), DOM assertions, and bounded content verification",
|
|
92
|
-
file: "testing.md",
|
|
93
|
-
},
|
|
94
|
-
];
|
|
95
|
-
|
|
96
|
-
const EXAMPLE_DESCRIPTIONS: { [key: string]: string } = {
|
|
97
|
-
init_sample:
|
|
98
|
-
"Complete starter template with all features (used by 'tk init')",
|
|
99
|
-
basic_build: "Simple HTML + TypeScript bundling",
|
|
100
|
-
with_assets: "HTML in multiple directories with asset references",
|
|
101
|
-
with_pre: "Pre-rendering HTML at build time with .pre.ts files",
|
|
102
|
-
with_com_html_priority:
|
|
103
|
-
"Static HTML components (.com.html) with local override priority",
|
|
104
|
-
with_com_ts: "TypeScript components (.com.ts) generating HTML at build time",
|
|
105
|
-
with_com_ts_priority:
|
|
106
|
-
"TypeScript components (.com.ts) with local override priority",
|
|
107
|
-
with_com_mixed_priority:
|
|
108
|
-
"Mixed .com.html and .com.ts showing processing order",
|
|
109
|
-
with_com_html_in_ts:
|
|
110
|
-
"HTML template (.com.html) injected into .com.ts as com.innerHTML before execution",
|
|
111
|
-
with_component_iteration:
|
|
112
|
-
"Component iteration: .com.ts with logic, .com.html for templates",
|
|
113
|
-
};
|
|
114
|
-
|
|
115
|
-
const readDirRecursive = (
|
|
116
|
-
dir: string,
|
|
117
|
-
baseDir: string = dir,
|
|
118
|
-
): { [key: string]: string } => {
|
|
119
|
-
const files: { [key: string]: string } = {};
|
|
120
|
-
const items = readdirSync(dir);
|
|
121
|
-
|
|
122
|
-
for (const item of items) {
|
|
123
|
-
const fullPath = join(dir, item);
|
|
124
|
-
const relativePath = fullPath.substring(baseDir.length + 1);
|
|
125
|
-
|
|
126
|
-
if (statSync(fullPath).isDirectory()) {
|
|
127
|
-
Object.assign(files, readDirRecursive(fullPath, baseDir));
|
|
128
|
-
} else {
|
|
129
|
-
files[relativePath] = readFileSync(fullPath, "utf-8");
|
|
130
|
-
}
|
|
131
|
-
}
|
|
132
|
-
|
|
133
|
-
return files;
|
|
134
|
-
};
|
|
135
|
-
|
|
136
|
-
const server = new McpServer({
|
|
137
|
-
name: "tkeron-mcp",
|
|
138
|
-
version: getVersion(),
|
|
139
|
-
});
|
|
140
|
-
|
|
141
|
-
for (const doc of DOCS) {
|
|
142
|
-
server.registerResource(
|
|
143
|
-
doc.name,
|
|
144
|
-
doc.uri,
|
|
145
|
-
{ description: doc.description, mimeType: "text/markdown" },
|
|
146
|
-
() => {
|
|
147
|
-
const filePath = join(DOCS_DIR, doc.file);
|
|
148
|
-
|
|
149
|
-
if (!existsSync(filePath)) {
|
|
150
|
-
throw new Error(`Documentation file not found: ${doc.file}`);
|
|
151
|
-
}
|
|
152
|
-
|
|
153
|
-
const content = readFileSync(filePath, "utf-8");
|
|
154
|
-
|
|
155
|
-
return {
|
|
156
|
-
contents: [
|
|
157
|
-
{
|
|
158
|
-
uri: doc.uri,
|
|
159
|
-
mimeType: "text/markdown",
|
|
160
|
-
text: content,
|
|
161
|
-
},
|
|
162
|
-
],
|
|
163
|
-
};
|
|
164
|
-
},
|
|
165
|
-
);
|
|
166
|
-
}
|
|
167
|
-
|
|
168
|
-
server.registerTool(
|
|
169
|
-
"list_examples",
|
|
170
|
-
{
|
|
171
|
-
description:
|
|
172
|
-
"List all available Tkeron example projects with their descriptions",
|
|
173
|
-
annotations: { readOnlyHint: true },
|
|
174
|
-
},
|
|
175
|
-
() => {
|
|
176
|
-
const examples = readdirSync(EXAMPLES_DIR).filter((name) => {
|
|
177
|
-
const examplePath = join(EXAMPLES_DIR, name);
|
|
178
|
-
return (
|
|
179
|
-
statSync(examplePath).isDirectory() &&
|
|
180
|
-
existsSync(join(examplePath, "websrc"))
|
|
181
|
-
);
|
|
182
|
-
});
|
|
183
|
-
|
|
184
|
-
const exampleList = examples.map((name) => ({
|
|
185
|
-
name,
|
|
186
|
-
description: EXAMPLE_DESCRIPTIONS[name] || "No description available",
|
|
187
|
-
path: `examples/${name}`,
|
|
188
|
-
}));
|
|
189
|
-
|
|
190
|
-
return {
|
|
191
|
-
content: [
|
|
192
|
-
{
|
|
193
|
-
type: "text" as const,
|
|
194
|
-
text: JSON.stringify(exampleList, null, 2),
|
|
195
|
-
},
|
|
196
|
-
],
|
|
197
|
-
};
|
|
198
|
-
},
|
|
199
|
-
);
|
|
200
|
-
|
|
201
|
-
server.registerTool(
|
|
202
|
-
"get_example",
|
|
203
|
-
{
|
|
204
|
-
description:
|
|
205
|
-
"Get the source code and structure of a specific Tkeron example project",
|
|
206
|
-
inputSchema: {
|
|
207
|
-
example: {
|
|
208
|
-
type: "string",
|
|
209
|
-
description:
|
|
210
|
-
"Example name (e.g., 'basic_build', 'with_component_iteration')",
|
|
211
|
-
},
|
|
212
|
-
} as any,
|
|
213
|
-
annotations: { readOnlyHint: true },
|
|
214
|
-
},
|
|
215
|
-
({ example: exampleName }: { example: string }) => {
|
|
216
|
-
const examplePath = join(EXAMPLES_DIR, exampleName);
|
|
217
|
-
|
|
218
|
-
if (!existsSync(examplePath)) {
|
|
219
|
-
return {
|
|
220
|
-
content: [
|
|
221
|
-
{
|
|
222
|
-
type: "text" as const,
|
|
223
|
-
text: `Example not found: ${exampleName}. Use the list_examples tool to see available examples.`,
|
|
224
|
-
},
|
|
225
|
-
],
|
|
226
|
-
isError: true,
|
|
227
|
-
};
|
|
228
|
-
}
|
|
229
|
-
|
|
230
|
-
const srcPath = join(examplePath, "websrc");
|
|
231
|
-
|
|
232
|
-
if (!existsSync(srcPath)) {
|
|
233
|
-
return {
|
|
234
|
-
content: [
|
|
235
|
-
{
|
|
236
|
-
type: "text" as const,
|
|
237
|
-
text: `Example ${exampleName} does not have a websrc directory`,
|
|
238
|
-
},
|
|
239
|
-
],
|
|
240
|
-
isError: true,
|
|
241
|
-
};
|
|
242
|
-
}
|
|
243
|
-
|
|
244
|
-
const sourceFiles = readDirRecursive(srcPath);
|
|
245
|
-
|
|
246
|
-
const result = {
|
|
247
|
-
example: exampleName,
|
|
248
|
-
path: `examples/${exampleName}`,
|
|
249
|
-
files: sourceFiles,
|
|
250
|
-
};
|
|
251
|
-
|
|
252
|
-
return {
|
|
253
|
-
content: [
|
|
254
|
-
{
|
|
255
|
-
type: "text" as const,
|
|
256
|
-
text: JSON.stringify(result, null, 2),
|
|
257
|
-
},
|
|
258
|
-
],
|
|
259
|
-
};
|
|
260
|
-
},
|
|
261
|
-
);
|
|
262
|
-
|
|
263
|
-
const main = async () => {
|
|
264
|
-
const transport = new StdioServerTransport();
|
|
265
|
-
await server.connect(transport);
|
|
266
|
-
console.error(`[tkeron-mcp] Server v${getVersion()} started`);
|
|
267
|
-
};
|
|
268
|
-
|
|
269
|
-
main().catch((error) => {
|
|
270
|
-
console.error(`[tkeron-mcp] Fatal error:`, error);
|
|
271
|
-
process.exit(1);
|
|
272
|
-
});
|
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
import { readdir, rm } from "fs/promises";
|
|
2
|
-
import { join } from "path";
|
|
3
|
-
import type { Logger } from "@tkeron/tools";
|
|
4
|
-
|
|
5
|
-
export const TEMP_DIR_PREFIX = ".tktmp_build-";
|
|
6
|
-
|
|
7
|
-
export const cleanupOrphanedTempDirs = async (
|
|
8
|
-
parentDir: string,
|
|
9
|
-
log: Logger,
|
|
10
|
-
): Promise<void> => {
|
|
11
|
-
try {
|
|
12
|
-
const entries = await readdir(parentDir, { withFileTypes: true });
|
|
13
|
-
const orphanedDirs = entries.filter(
|
|
14
|
-
(entry) => entry.isDirectory() && entry.name.startsWith(TEMP_DIR_PREFIX),
|
|
15
|
-
);
|
|
16
|
-
|
|
17
|
-
await Promise.all(
|
|
18
|
-
orphanedDirs.map(async (dir) => {
|
|
19
|
-
const dirPath = join(parentDir, dir.name);
|
|
20
|
-
try {
|
|
21
|
-
await rm(dirPath, { recursive: true, force: true });
|
|
22
|
-
log.log(`🧹 Cleaned up orphaned temp directory: ${dir.name}`);
|
|
23
|
-
} catch (error) {
|
|
24
|
-
log.warn(
|
|
25
|
-
`Warning: Failed to cleanup orphaned temp directory ${dirPath}`,
|
|
26
|
-
);
|
|
27
|
-
}
|
|
28
|
-
}),
|
|
29
|
-
);
|
|
30
|
-
} catch (error) {}
|
|
31
|
-
};
|
package/src/promptUser.ts
DELETED
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
export const promptUser = async (question: string): Promise<boolean> => {
|
|
2
|
-
const readline = await import("readline");
|
|
3
|
-
const rl = readline.createInterface({
|
|
4
|
-
input: process.stdin,
|
|
5
|
-
output: process.stdout,
|
|
6
|
-
});
|
|
7
|
-
|
|
8
|
-
return new Promise((resolve) => {
|
|
9
|
-
rl.question(question, (answer) => {
|
|
10
|
-
rl.close();
|
|
11
|
-
const response = answer.trim().toLowerCase();
|
|
12
|
-
resolve(response === "y" || response === "yes");
|
|
13
|
-
});
|
|
14
|
-
});
|
|
15
|
-
};
|