Files
SERVtomaste/temp/server.js

337 lines
9.2 KiB
JavaScript
Raw Normal View History

#!/usr/bin/env node
// MCP Server - exposes dalidou tools to Claude Code on Windows
import "dotenv/config";
import { Server } from "@modelcontextprotocol/sdk/server/index.js";
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
import {
CallToolRequestSchema,
ListToolsRequestSchema,
} from "@modelcontextprotocol/sdk/types.js";
import weather from "../tools/weather.js";
import gitea from "../tools/gitea.js";
import siemensDocs from "../tools/siemens-docs.js";
const server = new Server(
{
name: "dalidou-assistant",
version: "1.3.0",
},
{
capabilities: {
tools: {},
},
}
);
// List available tools
server.setRequestHandler(ListToolsRequestSchema, async () => {
return {
tools: [
// Weather tools
{
name: "get_current_weather",
description: "Get current weather conditions in Rouyn-Noranda (temperature, wind, conditions)",
inputSchema: {
type: "object",
properties: {},
required: []
}
},
{
name: "get_hourly_forecast",
description: "Get hourly weather forecast for planning activities",
inputSchema: {
type: "object",
properties: {
days: { type: "number", description: "Days to forecast (1-7)" }
}
}
},
{
name: "get_daily_forecast",
description: "Get daily weather forecast (highs, lows, conditions)",
inputSchema: {
type: "object",
properties: {
days: { type: "number", description: "Days to forecast (1-14)" }
}
}
},
{
name: "find_best_activity_windows",
description: "Find best time windows for outdoor activities based on weather",
inputSchema: {
type: "object",
properties: {
activity: {
type: "string",
description: "Activity: skiing, cross-country-skiing, hiking, mushroom-hunting"
},
days: { type: "number", description: "Days to search (1-7)" }
},
required: ["activity"]
}
},
{
name: "check_skiing_conditions",
description: "Check if current conditions are good for cross-country skiing",
inputSchema: {
type: "object",
properties: {}
}
},
// Gitea tools
{
name: "get_today_commits",
description: "Get all git commits made today from Gitea",
inputSchema: {
type: "object",
properties: {}
}
},
{
name: "get_recent_activity",
description: "Get recent git activity across all Gitea repos",
inputSchema: {
type: "object",
properties: {
days: { type: "number", description: "Days of history (default 7)" }
}
}
},
{
name: "list_repos",
description: "List all repositories on Gitea",
inputSchema: {
type: "object",
properties: {}
}
},
// Siemens Documentation tools
{
name: "siemens_docs_list",
description: "List available Siemens documentation categories, NX Open class IDs, and usage info",
inputSchema: {
type: "object",
properties: {}
}
},
{
name: "siemens_docs_search",
description: "Search Siemens Support Center documentation for a specific topic",
inputSchema: {
type: "object",
properties: {
query: {
type: "string",
description: "Search query (e.g., 'NXOpen Body.GetFaces', 'sketch constraints')"
},
product: {
type: "string",
description: "Product to search: nx, teamcenter, simcenter, nastran (default: nx)"
}
},
required: ["query"]
}
},
{
name: "siemens_docs_fetch",
description: "Fetch a specific Siemens documentation page by URL",
inputSchema: {
type: "object",
properties: {
url: {
type: "string",
description: "Full URL of the documentation page to fetch"
}
},
required: ["url"]
}
},
{
name: "siemens_auth_status",
description: "Check Siemens Support Center authentication status",
inputSchema: {
type: "object",
properties: {}
}
},
{
name: "siemens_login",
description: "Login to Siemens Support Center (use if session expired)",
inputSchema: {
type: "object",
properties: {}
}
},
// NX Open Python Reference tools
{
name: "nxopen_get_class",
description: "Get NX Open Python class documentation. Known classes: Session, Part, BasePart, PdmSession, CaeSession",
inputSchema: {
type: "object",
properties: {
className: {
type: "string",
description: "Class name (e.g., 'Session', 'Part', 'BasePart')"
}
},
required: ["className"]
}
},
{
name: "nxopen_get_index",
description: "Get NX Open Python Reference index pages (class list, functions, hierarchy)",
inputSchema: {
type: "object",
properties: {
indexType: {
type: "string",
description: "Index type: classes, annotated, hierarchy, functions, main (default: classes)"
}
}
}
},
{
name: "nxopen_fetch_page",
description: "Fetch any NX Open Python Reference page by page ID (e.g., 'a03318.html' for Session)",
inputSchema: {
type: "object",
properties: {
pagePath: {
type: "string",
description: "Page path (e.g., 'a03318.html', 'classes.html', 'functions_s.html')"
}
},
required: ["pagePath"]
}
}
]
};
});
// Handle tool calls
server.setRequestHandler(CallToolRequestSchema, async (request) => {
const { name, arguments: args } = request.params;
try {
let result;
switch (name) {
// Weather tools
case "get_current_weather":
result = await weather.getCurrentWeather();
break;
case "get_hourly_forecast":
result = await weather.getHourlyForecast(args?.days || 2);
break;
case "get_daily_forecast":
result = await weather.getDailyForecast(args?.days || 7);
break;
case "find_best_activity_windows":
result = await weather.findBestTimeWindows(args.activity, args?.days || 2);
break;
case "check_skiing_conditions":
const current = await weather.getCurrentWeather();
const skiCheck = weather.isGoodForSkiing(current);
result = {
current_weather: current,
good_for_skiing: skiCheck.good,
assessment: skiCheck.reasons
};
break;
// Gitea tools
case "get_today_commits":
result = await gitea.getAllTodayCommits();
break;
case "get_recent_activity":
result = await gitea.getRepoActivity(args?.days || 7);
break;
case "list_repos":
result = await gitea.listRepos();
break;
// Siemens Documentation tools
case "siemens_docs_list":
result = await siemensDocs.listAvailableDocs();
break;
case "siemens_docs_search":
result = await siemensDocs.searchDocs(args.query, args.product || "nx");
break;
case "siemens_docs_fetch":
result = await siemensDocs.fetchDocPage(args.url);
break;
case "siemens_auth_status":
result = await siemensDocs.checkAuthStatus();
break;
case "siemens_login":
result = await siemensDocs.performLogin();
break;
// NX Open Python Reference tools
case "nxopen_get_class":
result = await siemensDocs.fetchNXOpenClass(args.className);
break;
case "nxopen_get_index":
result = await siemensDocs.getNXOpenIndex(args?.indexType || "classes");
break;
case "nxopen_fetch_page":
result = await siemensDocs.fetchNXOpenPythonRef(args.pagePath);
break;
default:
return {
content: [{ type: "text", text: `Unknown tool: ${name}` }],
isError: true
};
}
return {
content: [{
type: "text",
text: typeof result === "string" ? result : JSON.stringify(result, null, 2)
}]
};
} catch (error) {
return {
content: [{ type: "text", text: `Error: ${error.message}` }],
isError: true
};
}
});
// Cleanup on exit
process.on("SIGINT", async () => {
await siemensDocs.closeBrowser();
process.exit(0);
});
process.on("SIGTERM", async () => {
await siemensDocs.closeBrowser();
process.exit(0);
});
// Start server
async function main() {
const transport = new StdioServerTransport();
await server.connect(transport);
console.error("Dalidou MCP Server v1.3.0 running on stdio (with NX Open Python Reference)");
}
main().catch(console.error);