auto commit

This commit is contained in:
bangdk 2024-11-10 08:51:18 +09:00
parent 83f95cd94b
commit 93b364be2e
5 changed files with 212 additions and 2 deletions

View File

@ -58,6 +58,11 @@ services:
depends_on:
- postgres
# - redis
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:3001/health"]
interval: 30s
timeout: 10s
retries: 3
postgres:
image: postgres:16-alpine

View File

@ -12,8 +12,8 @@ services:
# 개발 환경에서는 healthcheck 비활성화
volumes:
- ../../wacefems/uploads:/app/uploads
healthcheck:
disable: true
# healthcheck:
# disable: true
fems-app:
ports:

View File

@ -0,0 +1,80 @@
// src/controllers/app/health/health.controller.js
const express = require("express");
const router = express.Router();
const logger = require("../../../config/logger");
const { getSystemStatus } = require("../../../services/system.service");
// 기본 health check
router.get("/", async (req, res) => {
try {
// 시스템 기본 상태 반환
res.json({
status: "healthy",
timestamp: new Date().toISOString(),
serverTime: new Date().toISOString(),
});
} catch (error) {
logger.error("Health check failed:", error);
res.status(500).json({
status: "unhealthy",
timestamp: new Date().toISOString(),
error: error.message,
});
}
});
// 상세 health check
router.get("/detail", async (req, res) => {
try {
// 시스템 상세 상태 조회
const systemStatus = await getSystemStatus();
res.json({
status: "healthy",
timestamp: new Date().toISOString(),
serverTime: new Date().toISOString(),
details: {
database: systemStatus.database,
redis: systemStatus.redis,
services: systemStatus.services,
uptime: process.uptime(),
memory: process.memoryUsage(),
},
});
} catch (error) {
logger.error("Detailed health check failed:", error);
res.status(500).json({
status: "unhealthy",
timestamp: new Date().toISOString(),
error: error.message,
});
}
});
// Edge 서버 상태 확인용 특별 엔드포인트
router.get("/edge", async (req, res) => {
try {
const edgeId = req.header("X-Edge-ID");
logger.info(`Health check from Edge server: ${edgeId}`);
res.json({
status: "healthy",
timestamp: new Date().toISOString(),
serverTime: new Date().toISOString(),
edgeServer: {
id: edgeId,
lastCheck: new Date().toISOString(),
connectionStatus: "connected",
},
});
} catch (error) {
logger.error("Edge health check failed:", error);
res.status(500).json({
status: "unhealthy",
timestamp: new Date().toISOString(),
error: error.message,
});
}
});
module.exports = router;

View File

@ -13,7 +13,9 @@ const personnelController = require("../controllers/app/personnel/personnel.cont
const partsController = require("../controllers/app/parts/parts.controller");
const equipmentPartsController = require("../controllers/app/equipmentParts/equipmentParts.controller"); // 추가
const departmentController = require("../controllers/app/department/department.controller");
const healthController = require("../controllers/app/health/health.controller");
router.use("/health", healthController);
router.use("/auth", authController);
router.use("/users", usersController);
router.use("/dashboard", dashboardController);

View File

@ -0,0 +1,123 @@
// src/services/system.service.js
const Redis = require("ioredis");
const mongoose = require("mongoose");
const logger = require("../config/logger");
const config = require("../config/config");
class SystemService {
constructor() {
this.redis = new Redis(config.redis);
}
async getSystemStatus() {
try {
// Redis 상태 체크
// const redisStatus = await this.checkRedisStatus();
// 데이터베이스 상태 체크
// const dbStatus = await this.checkDatabaseStatus();
// 서비스 상태 체크
const servicesStatus = await this.checkServicesStatus();
return {
// database: dbStatus,
// redis: redisStatus,
services: servicesStatus,
};
} catch (error) {
logger.error("Failed to get system status:", error);
throw error;
}
}
// async checkRedisStatus() {
// try {
// await this.redis.ping();
// return {
// status: "healthy",
// latency: await this.measureRedisLatency(),
// };
// } catch (error) {
// logger.error("Redis health check failed:", error);
// return {
// status: "unhealthy",
// error: error.message,
// };
// }
// }
// async checkDatabaseStatus() {
// try {
// const status = mongoose.connection.readyState;
// const statusMap = {
// 0: "disconnected",
// 1: "connected",
// 2: "connecting",
// 3: "disconnecting",
// };
// return {
// status: status === 1 ? "healthy" : "unhealthy",
// state: statusMap[status],
// latency: await this.measureDatabaseLatency(),
// };
// } catch (error) {
// logger.error("Database health check failed:", error);
// return {
// status: "unhealthy",
// error: error.message,
// };
// }
// }
async checkServicesStatus() {
// 필요한 서비스들의 상태 체크
const services = {
api: await this.checkAPIStatus(),
scheduler: await this.checkSchedulerStatus(),
worker: await this.checkWorkerStatus(),
};
return services;
}
async measureRedisLatency() {
const start = process.hrtime();
await this.redis.ping();
const [seconds, nanoseconds] = process.hrtime(start);
return (seconds * 1000 + nanoseconds / 1000000).toFixed(2);
}
async measureDatabaseLatency() {
const start = process.hrtime();
await mongoose.connection.db.admin().ping();
const [seconds, nanoseconds] = process.hrtime(start);
return (seconds * 1000 + nanoseconds / 1000000).toFixed(2);
}
async checkAPIStatus() {
return {
status: "healthy",
uptime: process.uptime(),
};
}
async checkSchedulerStatus() {
// 스케줄러 상태 체크 로직
return {
status: "healthy",
lastRun: new Date().toISOString(),
};
}
async checkWorkerStatus() {
// 워커 상태 체크 로직
return {
status: "healthy",
activeWorkers: 0,
};
}
}
module.exports = new SystemService();