Skip to main content
Glama
health-check.js11.5 kB
#!/usr/bin/env node /** * WordPress MCP Server - Simple Health Check * Quick diagnostic script for basic system health without complex dependencies */ import { createRequire } from "module"; import { fileURLToPath } from "url"; import { dirname, join } from "path"; import { spawn } from "child_process"; const require = createRequire(import.meta.url); const __filename = fileURLToPath(import.meta.url); const __dirname = dirname(__filename); const projectRoot = join(__dirname, ".."); // Simple console colors const colors = { reset: "\x1b[0m", bright: "\x1b[1m", red: "\x1b[31m", green: "\x1b[32m", yellow: "\x1b[33m", blue: "\x1b[34m", cyan: "\x1b[36m", }; const log = (message, type = "info") => { const prefix = { info: `${colors.blue}ℹ️${colors.reset}`, success: `${colors.green}✅${colors.reset}`, error: `${colors.red}❌${colors.reset}`, warning: `${colors.yellow}⚠️${colors.reset}`, test: `${colors.cyan}🔧${colors.reset}`, }[type]; console.log(`${prefix} ${message}`); }; const header = (title) => { console.log(`\n${colors.bright}${colors.blue}${title}${colors.reset}`); console.log("=".repeat(50)); }; /** * Check if required files exist */ function checkProjectStructure() { header("📁 Project Structure Check"); const requiredFiles = [ "package.json", "src/index.ts", "src/client/api.ts", "src/client/auth.ts", "tsconfig.json", "dist/index.js", ]; let allFilesExist = true; for (const file of requiredFiles) { try { const fs = require("fs"); const filePath = join(projectRoot, file); if (fs.existsSync(filePath)) { log(`${file} - Found`, "success"); } else { log(`${file} - Missing`, "error"); allFilesExist = false; } } catch (error) { log(`${file} - Check failed: ${error.message}`, "error"); allFilesExist = false; } } return allFilesExist; } /** * Check Node.js and NPM versions */ function checkNodeEnvironment() { header("🌐 Node.js Environment Check"); try { const nodeVersion = process.version; const majorVersion = parseInt(nodeVersion.slice(1).split(".")[0]); log(`Node.js version: ${nodeVersion}`, majorVersion >= 18 ? "success" : "warning"); if (majorVersion < 18) { log("Recommended: Node.js 18 or higher", "warning"); } // Check if npm is available return new Promise((resolve) => { const npmProcess = spawn("npm", ["--version"], { stdio: "pipe" }); let npmVersion = ""; npmProcess.stdout.on("data", (data) => { npmVersion += data.toString().trim(); }); npmProcess.on("close", (code) => { if (code === 0) { log(`NPM version: ${npmVersion}`, "success"); } else { log("NPM not found or error", "error"); } resolve(code === 0); }); npmProcess.on("error", () => { log("NPM not found", "error"); resolve(false); }); }); } catch (error) { log(`Environment check failed: ${error.message}`, "error"); return false; } } /** * Check if project dependencies are installed */ function checkDependencies() { header("📦 Dependencies Check"); try { const fs = require("fs"); const packagePath = join(projectRoot, "package.json"); const nodeModulesPath = join(projectRoot, "node_modules"); if (!fs.existsSync(packagePath)) { log("package.json not found", "error"); return false; } const packageJson = JSON.parse(fs.readFileSync(packagePath, "utf8")); log(`Project: ${packageJson.name} v${packageJson.version}`, "info"); if (!fs.existsSync(nodeModulesPath)) { log("node_modules not found - run 'npm install'", "error"); return false; } log("node_modules directory exists", "success"); // Check for key dependencies const keyDeps = ["@modelcontextprotocol/sdk", "typescript", "dotenv", "form-data"]; // Optional dependencies (nice to have but not required for CI) const optionalDeps = ["node-fetch"]; let depsOk = true; for (const dep of keyDeps) { const depPath = join(nodeModulesPath, dep); if (fs.existsSync(depPath)) { log(`${dep} - Installed`, "success"); } else { log(`${dep} - Missing`, "error"); depsOk = false; } } // Check optional dependencies (doesn't affect health status) for (const dep of optionalDeps) { const depPath = join(nodeModulesPath, dep); if (fs.existsSync(depPath)) { log(`${dep} - Installed (optional)`, "success"); } else { log(`${dep} - Missing (optional, using native fetch)`, "info"); } } return depsOk; } catch (error) { log(`Dependencies check failed: ${error.message}`, "error"); return false; } } /** * Check TypeScript compilation */ function checkTypeScriptBuild() { header("🔨 TypeScript Build Check"); return new Promise((resolve) => { const tscProcess = spawn("npx", ["tsc", "--noEmit"], { cwd: projectRoot, stdio: "pipe", }); let stdout = ""; let stderr = ""; tscProcess.stdout.on("data", (data) => { stdout += data.toString(); }); tscProcess.stderr.on("data", (data) => { stderr += data.toString(); }); tscProcess.on("close", (code) => { if (code === 0) { log("TypeScript compilation check passed", "success"); resolve(true); } else { log("TypeScript compilation errors found", "error"); if (stderr) { console.log(stderr); } resolve(false); } }); tscProcess.on("error", (error) => { log(`TypeScript check failed: ${error.message}`, "error"); resolve(false); }); }); } /** * Check environment configuration */ function checkEnvironmentConfig() { header("🔐 Environment Configuration Check"); try { const fs = require("fs"); const envPath = join(projectRoot, ".env"); if (!fs.existsSync(envPath)) { log(".env file not found", "warning"); log("Run 'npm run setup' to configure", "info"); // In CI environments, missing .env is expected if (process.env.CI || process.env.NODE_ENV === "test") { log("CI environment detected - .env file not required", "info"); return true; } return false; } const envContent = fs.readFileSync(envPath, "utf8"); const envLines = envContent.split("\n").filter((line) => line.trim() && !line.trim().startsWith("#")); const requiredVars = ["WORDPRESS_SITE_URL", "WORDPRESS_USERNAME"]; let configOk = true; for (const varName of requiredVars) { const found = envLines.some((line) => line.startsWith(`${varName}=`)); if (found) { log(`${varName} - Configured`, "success"); } else { log(`${varName} - Missing`, "error"); configOk = false; } } // Check for at least one auth method const authMethods = ["WORDPRESS_APP_PASSWORD", "WORDPRESS_PASSWORD", "WORDPRESS_API_KEY", "WORDPRESS_JWT_SECRET"]; const hasAuthMethod = authMethods.some((method) => envLines.some((line) => line.startsWith(`${method}=`))); if (hasAuthMethod) { log("Authentication method configured", "success"); } else { log("No authentication method found", "error"); configOk = false; } return configOk; } catch (error) { log(`Environment check failed: ${error.message}`, "error"); return false; } } /** * Check if compiled JavaScript exists */ function checkCompiledOutput() { header("📦 Compiled Output Check"); try { const fs = require("fs"); const distPath = join(projectRoot, "dist"); if (!fs.existsSync(distPath)) { log("dist directory not found - run 'npm run build'", "error"); return false; } const keyFiles = ["index.js", "client/api.js", "client/auth.js", "tools/posts.js"]; let allCompiledFilesExist = true; for (const file of keyFiles) { const filePath = join(distPath, file); if (fs.existsSync(filePath)) { log(`${file} - Compiled`, "success"); } else { log(`${file} - Missing`, "error"); allCompiledFilesExist = false; } } return allCompiledFilesExist; } catch (error) { log(`Compiled output check failed: ${error.message}`, "error"); return false; } } /** * Main health check function */ async function runHealthCheck() { console.log(`${colors.bright}${colors.cyan}🏥 WordPress MCP Server - Health Check${colors.reset}`); console.log("=".repeat(60)); console.log(`📍 Project Root: ${projectRoot}`); const checks = [ { name: "Node Environment", fn: checkNodeEnvironment }, { name: "Project Structure", fn: checkProjectStructure }, { name: "Dependencies", fn: checkDependencies }, { name: "Environment Config", fn: checkEnvironmentConfig }, { name: "TypeScript Build", fn: checkTypeScriptBuild }, { name: "Compiled Output", fn: checkCompiledOutput }, ]; const results = []; let passedChecks = 0; for (const check of checks) { try { const result = await check.fn(); results.push({ name: check.name, passed: result }); if (result) passedChecks++; } catch (error) { log(`${check.name} check failed: ${error.message}`, "error"); results.push({ name: check.name, passed: false }); } } // Summary header("📊 Health Check Summary"); const successRate = Math.round((passedChecks / checks.length) * 100); results.forEach((result) => { log(`${result.name}: ${result.passed ? "PASS" : "FAIL"}`, result.passed ? "success" : "error"); }); console.log(`\n${colors.bright}Overall Health: ${successRate}%${colors.reset}`); if (successRate === 100) { log("🎉 All health checks passed! System is ready.", "success"); } else if (successRate >= 80) { log("⚠️ Most checks passed. Minor issues detected.", "warning"); } else { log("❌ Multiple issues detected. Please fix before proceeding.", "error"); } // Recommendations if (successRate < 100) { console.log(`\n${colors.bright}🔧 Recommended Actions:${colors.reset}`); if (!results.find((r) => r.name === "Dependencies")?.passed) { console.log("• Run: npm install"); } if (!results.find((r) => r.name === "Environment Config")?.passed) { console.log("• Run: npm run setup"); } if (!results.find((r) => r.name === "TypeScript Build")?.passed) { console.log("• Fix TypeScript errors and run: npm run build"); } if (!results.find((r) => r.name === "Compiled Output")?.passed) { console.log("• Run: npm run build"); } console.log("• Check the documentation: README.md"); console.log("• Run: npm run status (for WordPress connection check)"); } console.log(""); // In CI environments, be more lenient with success rate const isCI = process.env.CI || process.env.NODE_ENV === "test"; const requiredSuccessRate = isCI ? 83 : 100; // Allow 5/6 checks to pass in CI if (isCI && successRate >= requiredSuccessRate) { log("🎉 CI environment: Essential checks passed, system is operational.", "success"); } process.exit(successRate >= requiredSuccessRate ? 0 : 1); } // Run health check runHealthCheck().catch((error) => { log(`Health check failed: ${error.message}`, "error"); console.error(error.stack); process.exit(1); });

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/docdyhr/mcp-wordpress'

If you have feedback or need assistance with the MCP directory API, please join our Discord server