@atlisp/mcp 1.4.0 → 1.4.1
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/dist/atlisp-mcp.js +115 -95
- package/package.json +1 -1
package/dist/atlisp-mcp.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
|
|
3
3
|
// src/atlisp-mcp.js
|
|
4
|
-
import
|
|
5
|
-
import { fileURLToPath as
|
|
4
|
+
import path5 from "path";
|
|
5
|
+
import { fileURLToPath as fileURLToPath3 } from "url";
|
|
6
6
|
import { createRequire } from "module";
|
|
7
7
|
import express from "express";
|
|
8
8
|
import rawBody from "raw-body";
|
|
@@ -794,6 +794,11 @@ ${allFuncs.map((f) => f.name).join("\n")}` }] };
|
|
|
794
794
|
}
|
|
795
795
|
|
|
796
796
|
// src/handlers/resource-handlers.js
|
|
797
|
+
import fs3 from "fs";
|
|
798
|
+
import path4 from "path";
|
|
799
|
+
import { fileURLToPath as fileURLToPath2 } from "url";
|
|
800
|
+
var __dirname2 = path4.dirname(fileURLToPath2(import.meta.url));
|
|
801
|
+
var STANDARDS_DIR = path4.join(__dirname2, "..", "standards");
|
|
797
802
|
var CACHE_TTL2 = config_default.resourceCacheTtl;
|
|
798
803
|
var resourceCache = /* @__PURE__ */ new Map();
|
|
799
804
|
function getCached(key) {
|
|
@@ -888,12 +893,15 @@ function parseLispList(str) {
|
|
|
888
893
|
}
|
|
889
894
|
var RESOURCES = [
|
|
890
895
|
{ uri: "atlisp://cad/info", name: "CAD Info", description: "CAD \u8FDE\u63A5\u4FE1\u606F", mimeType: "application/json", subscribable: true },
|
|
891
|
-
{ uri: "atlisp://
|
|
892
|
-
{ uri: "atlisp://
|
|
896
|
+
{ uri: "atlisp://dwg/layers", name: "Layers", description: "\u56FE\u5C42\u5217\u8868", mimeType: "application/json", subscribable: true },
|
|
897
|
+
{ uri: "atlisp://dwg/entities", name: "Entities", description: "\u5B9E\u4F53\u7EDF\u8BA1", mimeType: "application/json", subscribable: true },
|
|
893
898
|
{ uri: "atlisp://dwg/name", name: "DWG Name", description: "\u5F53\u524D DWG \u6587\u4EF6\u540D", mimeType: "application/json", subscribable: true },
|
|
894
899
|
{ uri: "atlisp://dwg/path", name: "DWG Path", description: "\u6587\u4EF6\u5B8C\u6574\u8DEF\u5F84", mimeType: "application/json", subscribable: true },
|
|
900
|
+
{ uri: "atlisp://cad/dwgs", name: "DWG List", description: "\u6240\u6709\u6253\u5F00\u7684 DWG \u6587\u4EF6\u5217\u8868", mimeType: "application/json", subscribable: true },
|
|
895
901
|
{ uri: "atlisp://packages", name: "Packages", description: "\u5DF2\u5B89\u88C5\u5305\u5217\u8868", mimeType: "application/json", subscribable: true },
|
|
896
|
-
{ uri: "atlisp://platforms", name: "Platforms", description: "\u652F\u6301\u7684\u5E73\u53F0\u4FE1\u606F", mimeType: "application/json", subscribable: false }
|
|
902
|
+
{ uri: "atlisp://platforms", name: "Platforms", description: "\u652F\u6301\u7684\u5E73\u53F0\u4FE1\u606F", mimeType: "application/json", subscribable: false },
|
|
903
|
+
{ uri: "atlisp://standards/drafting", name: "Drafting Standards", description: "CAD \u5236\u56FE\u89C4\u8303", mimeType: "application/json", subscribable: false },
|
|
904
|
+
{ uri: "atlisp://standards/coding", name: "Coding Standards", description: "@lisp \u7F16\u7801\u89C4\u8303", mimeType: "application/json", subscribable: false }
|
|
897
905
|
];
|
|
898
906
|
function parseQuery(uri) {
|
|
899
907
|
const qIdx = uri.indexOf("?");
|
|
@@ -924,18 +932,24 @@ async function readResource(uri) {
|
|
|
924
932
|
switch (base) {
|
|
925
933
|
case "atlisp://cad/info":
|
|
926
934
|
return await getCadInfo2();
|
|
927
|
-
case "atlisp://
|
|
935
|
+
case "atlisp://dwg/layers":
|
|
928
936
|
return await getLayers(params.name);
|
|
929
|
-
case "atlisp://
|
|
937
|
+
case "atlisp://dwg/entities":
|
|
930
938
|
return await getEntities(params.type);
|
|
931
939
|
case "atlisp://dwg/name":
|
|
932
940
|
return await getDwgName();
|
|
933
941
|
case "atlisp://dwg/path":
|
|
934
942
|
return await getDwgPath();
|
|
943
|
+
case "atlisp://cad/dwgs":
|
|
944
|
+
return await getDwgList();
|
|
935
945
|
case "atlisp://packages":
|
|
936
946
|
return await getPackages(params.name);
|
|
937
947
|
case "atlisp://platforms":
|
|
938
948
|
return getPlatforms();
|
|
949
|
+
case "atlisp://standards/drafting":
|
|
950
|
+
return getDraftingStandards();
|
|
951
|
+
case "atlisp://standards/coding":
|
|
952
|
+
return getCodingStandards();
|
|
939
953
|
default:
|
|
940
954
|
throw new Error(`\u8D44\u6E90\u4E0D\u5B58\u5728: ${uri}`);
|
|
941
955
|
}
|
|
@@ -968,7 +982,7 @@ async function getCadInfo2() {
|
|
|
968
982
|
return result;
|
|
969
983
|
}
|
|
970
984
|
async function getLayers(filterName = null) {
|
|
971
|
-
const cacheKey = filterName ? `layers:${filterName}` : "layers:all";
|
|
985
|
+
const cacheKey = filterName ? `dwg:layers:${filterName}` : "dwg:layers:all";
|
|
972
986
|
const cached = getCached(cacheKey);
|
|
973
987
|
if (cached)
|
|
974
988
|
return cached;
|
|
@@ -1020,7 +1034,7 @@ async function getLayers(filterName = null) {
|
|
|
1020
1034
|
}
|
|
1021
1035
|
}
|
|
1022
1036
|
async function getEntities(filterType = null) {
|
|
1023
|
-
const cacheKey = filterType ? `entities:${filterType}` : "entities:all";
|
|
1037
|
+
const cacheKey = filterType ? `dwg:entities:${filterType}` : "dwg:entities:all";
|
|
1024
1038
|
const cached = getCached(cacheKey);
|
|
1025
1039
|
if (cached)
|
|
1026
1040
|
return cached;
|
|
@@ -1197,26 +1211,95 @@ function getPlatforms() {
|
|
|
1197
1211
|
extensions: FILE_EXTENSIONS[name] || []
|
|
1198
1212
|
}));
|
|
1199
1213
|
}
|
|
1214
|
+
async function getDwgList() {
|
|
1215
|
+
const cacheKey = "cad:dwgs";
|
|
1216
|
+
const cached = getCached(cacheKey);
|
|
1217
|
+
if (cached)
|
|
1218
|
+
return cached;
|
|
1219
|
+
if (!cad.connected)
|
|
1220
|
+
await cad.connect();
|
|
1221
|
+
if (!cad.connected)
|
|
1222
|
+
return [];
|
|
1223
|
+
try {
|
|
1224
|
+
const code = `(progn
|
|
1225
|
+
(vl-load-com)
|
|
1226
|
+
(setq result nil)
|
|
1227
|
+
(vlax-for doc (vla-get-Documents (vla-get-Application (vlax-get-acad-object)))
|
|
1228
|
+
(setq result (cons (list (vla-get-Name doc) (vla-get-FullName doc)) result))
|
|
1229
|
+
)
|
|
1230
|
+
(reverse result)
|
|
1231
|
+
)`;
|
|
1232
|
+
const result = await cad.sendCommandWithResult(code);
|
|
1233
|
+
if (!result || result === "" || result === "nil") {
|
|
1234
|
+
setCache(cacheKey, []);
|
|
1235
|
+
return [];
|
|
1236
|
+
}
|
|
1237
|
+
let parsed = [];
|
|
1238
|
+
try {
|
|
1239
|
+
parsed = JSON.parse(result);
|
|
1240
|
+
} catch (e) {
|
|
1241
|
+
const listResult = parseLispList(result);
|
|
1242
|
+
if (listResult) {
|
|
1243
|
+
parsed = listResult;
|
|
1244
|
+
}
|
|
1245
|
+
}
|
|
1246
|
+
if (!Array.isArray(parsed))
|
|
1247
|
+
parsed = [];
|
|
1248
|
+
const dwgList = parsed.map((item) => {
|
|
1249
|
+
if (Array.isArray(item) && item.length >= 2) {
|
|
1250
|
+
return { name: String(item[0]), path: String(item[1]) };
|
|
1251
|
+
}
|
|
1252
|
+
return null;
|
|
1253
|
+
}).filter(Boolean);
|
|
1254
|
+
setCache(cacheKey, dwgList);
|
|
1255
|
+
return dwgList;
|
|
1256
|
+
} catch (e) {
|
|
1257
|
+
setCache(cacheKey, []);
|
|
1258
|
+
return [];
|
|
1259
|
+
}
|
|
1260
|
+
}
|
|
1261
|
+
function loadStandardsFile(filename) {
|
|
1262
|
+
const filePath = path4.join(STANDARDS_DIR, filename);
|
|
1263
|
+
try {
|
|
1264
|
+
const raw = fs3.readFileSync(filePath, "utf-8");
|
|
1265
|
+
return JSON.parse(raw);
|
|
1266
|
+
} catch (e) {
|
|
1267
|
+
log(`Error loading standards file ${filename}: ${e.message}`);
|
|
1268
|
+
return null;
|
|
1269
|
+
}
|
|
1270
|
+
}
|
|
1271
|
+
var standardsCache = /* @__PURE__ */ new Map();
|
|
1272
|
+
function getCachedStandards(key) {
|
|
1273
|
+
const entry = standardsCache.get(key);
|
|
1274
|
+
if (entry && Date.now() - entry.timestamp < 3e4)
|
|
1275
|
+
return entry.data;
|
|
1276
|
+
standardsCache.delete(key);
|
|
1277
|
+
return null;
|
|
1278
|
+
}
|
|
1279
|
+
function setCachedStandards(key, data) {
|
|
1280
|
+
standardsCache.set(key, { data, timestamp: Date.now() });
|
|
1281
|
+
}
|
|
1282
|
+
function getDraftingStandards() {
|
|
1283
|
+
const cached = getCachedStandards("drafting");
|
|
1284
|
+
if (cached)
|
|
1285
|
+
return cached;
|
|
1286
|
+
const data = loadStandardsFile("drafting.json");
|
|
1287
|
+
if (data)
|
|
1288
|
+
setCachedStandards("drafting", data);
|
|
1289
|
+
return data || { error: "\u5236\u56FE\u89C4\u8303\u6587\u4EF6\u52A0\u8F7D\u5931\u8D25" };
|
|
1290
|
+
}
|
|
1291
|
+
function getCodingStandards() {
|
|
1292
|
+
const cached = getCachedStandards("coding");
|
|
1293
|
+
if (cached)
|
|
1294
|
+
return cached;
|
|
1295
|
+
const data = loadStandardsFile("coding.json");
|
|
1296
|
+
if (data)
|
|
1297
|
+
setCachedStandards("coding", data);
|
|
1298
|
+
return data || { error: "\u7F16\u7801\u89C4\u8303\u6587\u4EF6\u52A0\u8F7D\u5931\u8D25" };
|
|
1299
|
+
}
|
|
1200
1300
|
|
|
1201
1301
|
// src/handlers/prompt-handlers.js
|
|
1202
1302
|
var PROMPTS = [
|
|
1203
|
-
{
|
|
1204
|
-
name: "draw-residential",
|
|
1205
|
-
description: "\u751F\u6210\u519C\u6751\u6C11\u5C45\u5E73\u9762\u5E03\u7F6E\u56FE",
|
|
1206
|
-
arguments: [
|
|
1207
|
-
{ name: "width", description: "\u5EFA\u7B51\u5BBD\u5EA6 (mm)", required: true },
|
|
1208
|
-
{ name: "depth", description: "\u5EFA\u7B51\u6DF1\u5EA6 (mm)", required: true },
|
|
1209
|
-
{ name: "rooms", description: "\u623F\u95F4\u6570\u91CF", required: false }
|
|
1210
|
-
]
|
|
1211
|
-
},
|
|
1212
|
-
{
|
|
1213
|
-
name: "draw-floor-plan",
|
|
1214
|
-
description: "\u751F\u6210\u5EFA\u7B51\u697C\u5C42\u5E73\u9762\u56FE",
|
|
1215
|
-
arguments: [
|
|
1216
|
-
{ name: "floor", description: "\u697C\u5C42\u540D\u79F0", required: true },
|
|
1217
|
-
{ name: "scale", description: "\u56FE\u7EB8\u6BD4\u4F8B", required: false }
|
|
1218
|
-
]
|
|
1219
|
-
},
|
|
1220
1303
|
{
|
|
1221
1304
|
name: "analyze-drawing",
|
|
1222
1305
|
description: "\u5206\u6790\u5F53\u524D\u56FE\u7EB8\u7EDF\u8BA1\u4FE1\u606F",
|
|
@@ -1336,10 +1419,6 @@ async function listPrompts() {
|
|
|
1336
1419
|
}
|
|
1337
1420
|
async function getPrompt(name, arguments_ = {}) {
|
|
1338
1421
|
switch (name) {
|
|
1339
|
-
case "draw-residential":
|
|
1340
|
-
return generateResidentialPrompt(arguments_);
|
|
1341
|
-
case "draw-floor-plan":
|
|
1342
|
-
return generateFloorPlanPrompt(arguments_);
|
|
1343
1422
|
case "analyze-drawing":
|
|
1344
1423
|
return generateAnalyzePrompt();
|
|
1345
1424
|
case "batch-draw-lines":
|
|
@@ -1372,65 +1451,6 @@ async function getPrompt(name, arguments_ = {}) {
|
|
|
1372
1451
|
throw new Error(`Unknown prompt: ${name}`);
|
|
1373
1452
|
}
|
|
1374
1453
|
}
|
|
1375
|
-
async function generateResidentialPrompt(args) {
|
|
1376
|
-
const { width = 15e3, depth = 12e3, rooms = 6 } = args;
|
|
1377
|
-
const code = `(defun c:draw-residential (/ old-layer p)
|
|
1378
|
-
(setq old-layer (getvar "clayer"))
|
|
1379
|
-
(setvar "clayer" "0")
|
|
1380
|
-
(setq p (list 0 0))
|
|
1381
|
-
(command "_.rectangle" p (list ${width} ${depth}))
|
|
1382
|
-
${generateRoomLayout(width, depth, rooms)}
|
|
1383
|
-
(setvar "clayer" old-layer)
|
|
1384
|
-
(princ)
|
|
1385
|
-
)
|
|
1386
|
-
(c:draw-residential)`;
|
|
1387
|
-
return {
|
|
1388
|
-
messages: [{
|
|
1389
|
-
role: "user",
|
|
1390
|
-
content: {
|
|
1391
|
-
type: "text",
|
|
1392
|
-
text: `\u8BF7\u5728 CAD \u4E2D\u7ED8\u5236\u519C\u6751\u6C11\u5C45\u5E73\u9762\u56FE\uFF0C\u5C3A\u5BF8 ${width}x${depth}mm\uFF0C${rooms} \u4E2A\u623F\u95F4\u3002
|
|
1393
|
-
|
|
1394
|
-
\u751F\u6210\u7684 AutoLISP \u4EE3\u7801\uFF1A
|
|
1395
|
-
\`\`\`lisp
|
|
1396
|
-
${code}
|
|
1397
|
-
\`\`\`
|
|
1398
|
-
|
|
1399
|
-
\u76F4\u63A5\u6267\u884C\u6B64\u4EE3\u7801\u5373\u53EF\u751F\u6210\u56FE\u7EB8\u3002`
|
|
1400
|
-
}
|
|
1401
|
-
}]
|
|
1402
|
-
};
|
|
1403
|
-
}
|
|
1404
|
-
function generateRoomLayout(width, depth, rooms) {
|
|
1405
|
-
if (rooms === 6) {
|
|
1406
|
-
return `(command "_.line" (list 5000 0) (list 5000 ${depth}) "")
|
|
1407
|
-
(command "_.line" (list 0 4000) (list ${width} 4000) "")
|
|
1408
|
-
(command "_.text" "j" "c" "2500,2000" 800 0 "\u5BA2\u5385")
|
|
1409
|
-
(command "_.text" "j" "c" "7500,6000" 800 0 "\u9910\u5385")
|
|
1410
|
-
(command "_.text" "j" "c" "12500,2000" 800 0 "\u4E3B\u5367")`;
|
|
1411
|
-
}
|
|
1412
|
-
return `(command "_.text" "j" "c" (list (/ ${width} 2) (/ ${depth} 2)) 800 0 "\u623F\u95F4")`;
|
|
1413
|
-
}
|
|
1414
|
-
async function generateFloorPlanPrompt(args) {
|
|
1415
|
-
const { floor = "\u4E00\u5C42", scale = "1:100" } = args;
|
|
1416
|
-
return {
|
|
1417
|
-
messages: [{
|
|
1418
|
-
role: "user",
|
|
1419
|
-
content: {
|
|
1420
|
-
type: "text",
|
|
1421
|
-
text: `\u751F\u6210 ${floor} \u5E73\u9762\u56FE\uFF0C\u6BD4\u4F8B ${scale}\u3002
|
|
1422
|
-
|
|
1423
|
-
\u63D0\u793A\uFF1A
|
|
1424
|
-
1. \u4F7F\u7528 RECTANGLE \u547D\u4EE4\u7ED8\u5236\u5916\u5899
|
|
1425
|
-
2. \u4F7F\u7528 LINE \u547D\u4EE4\u7ED8\u5236\u5185\u90E8\u9694\u5899
|
|
1426
|
-
3. \u4F7F\u7528 TEXT \u547D\u4EE4\u6DFB\u52A0\u623F\u95F4\u6807\u6CE8
|
|
1427
|
-
4. \u4F7F\u7528 DIMLINEAR \u6216 DIMALIGNED \u6DFB\u52A0\u5C3A\u5BF8\u6807\u6CE8
|
|
1428
|
-
|
|
1429
|
-
\u9700\u8981\u6211\u6267\u884C\u54EA\u4E9B\u64CD\u4F5C\uFF1F`
|
|
1430
|
-
}
|
|
1431
|
-
}]
|
|
1432
|
-
};
|
|
1433
|
-
}
|
|
1434
1454
|
async function generateAnalyzePrompt() {
|
|
1435
1455
|
let entities = { total: 0, byType: {} };
|
|
1436
1456
|
let layers = [];
|
|
@@ -2289,8 +2309,8 @@ var SseSession = class {
|
|
|
2289
2309
|
sendMessage(data) {
|
|
2290
2310
|
return this.sendEvent(SSE_EVENTS.MESSAGE, data);
|
|
2291
2311
|
}
|
|
2292
|
-
sendEndpoint(
|
|
2293
|
-
return this.sendEvent(SSE_EVENTS.ENDPOINT,
|
|
2312
|
+
sendEndpoint(path6) {
|
|
2313
|
+
return this.sendEvent(SSE_EVENTS.ENDPOINT, path6);
|
|
2294
2314
|
}
|
|
2295
2315
|
sendError(code, message, id = null) {
|
|
2296
2316
|
return this.sendEvent(SSE_EVENTS.ERROR, { code, message }, id);
|
|
@@ -2456,9 +2476,9 @@ var SseSessionManager = class {
|
|
|
2456
2476
|
};
|
|
2457
2477
|
|
|
2458
2478
|
// src/atlisp-mcp.js
|
|
2459
|
-
var
|
|
2479
|
+
var __dirname3 = path5.dirname(fileURLToPath3(import.meta.url));
|
|
2460
2480
|
var require2 = createRequire(import.meta.url);
|
|
2461
|
-
var { version } = require2(
|
|
2481
|
+
var { version } = require2(path5.join(__dirname3, "..", "package.json"));
|
|
2462
2482
|
var isMcpScript = process.argv[1]?.includes("atlisp-mcp");
|
|
2463
2483
|
if (isMcpScript) {
|
|
2464
2484
|
const args = process.argv.slice(2);
|
|
@@ -2743,8 +2763,8 @@ async function handleToolCall(name, args) {
|
|
|
2743
2763
|
}
|
|
2744
2764
|
function notifyResourceChanges(toolName) {
|
|
2745
2765
|
const resourceMap = {
|
|
2746
|
-
connect_cad: ["atlisp://cad/info", "atlisp://
|
|
2747
|
-
new_document: ["atlisp://dwg/name", "atlisp://dwg/path", "atlisp://cad/layers", "atlisp://
|
|
2766
|
+
connect_cad: ["atlisp://cad/info", "atlisp://dwg/layers", "atlisp://dwg/name", "atlisp://dwg/path", "atlisp://cad/dwgs", "atlisp://packages"],
|
|
2767
|
+
new_document: ["atlisp://dwg/name", "atlisp://dwg/path", "atlisp://cad/dwgs", "atlisp://dwg/layers", "atlisp://dwg/entities"],
|
|
2748
2768
|
install_package: ["atlisp://packages"],
|
|
2749
2769
|
install_atlisp: ["atlisp://packages", "atlisp://cad/info"],
|
|
2750
2770
|
init_atlisp: ["atlisp://packages", "atlisp://cad/info"]
|