Merge krystie-improvements into main
Resolves 24 conflicts between Hermes (DC-008/009/010 + response-helper
envelope standardization) and Krystie (DC-005 src/ refactor path fixes,
DC-006 TOTP integration, DC-007 new test suites, cloud backup
destinations).
Conflict resolutions:
- src/utils/logging.js: took ours (consumers depend on logError/
safeErrorMessage/createLogger exports)
- src/config/site.js: merged (her factored validateAndLogConfig +
applyConfigFields helpers)
- src/context/dns.js: took hers (admin/readonly role iteration for
write operations)
- src/utilities/backup-
manager.js: took hers (Dropbox/WebDAV/SFTP cloud feature)
- status/dist/*, status/
sw.js: took hers (minified bundles + newer SW cache)
Additional fix (post-merge regression):
- src/monitoring/health-checker.js: fixed DC-005 path miss —
'require(./platform-paths)' → 'require(../../platform-paths)'
Test status: 921/922 passing. One known failure in logging.test.js
(async file-handle timing) tracked as follow-up.
This commit is contained in:
@@ -2,13 +2,13 @@ const express = require('express');
|
||||
const fs = require('fs');
|
||||
const path = require('path');
|
||||
const { execSync } = require('child_process');
|
||||
const { TIMEOUTS } = require('../constants');
|
||||
const { exists } = require('../fs-helpers');
|
||||
const { paginate, parsePaginationParams } = require('../pagination');
|
||||
const { TIMEOUTS } = require('../src/utilities/constants');
|
||||
const { exists } = require('../src/utilities/fs-helpers');
|
||||
const { paginate, parsePaginationParams } = require('../src/utilities/pagination');
|
||||
const platformPaths = require('../platform-paths');
|
||||
const { resolveServiceUrl } = require('../url-resolver');
|
||||
const { success, error: errorResponse } = require('../response-helpers');
|
||||
const { ValidationError } = require('../errors');
|
||||
const { resolveServiceUrl } = require('../src/utilities/url-resolver');
|
||||
const { success, error: errorResponse, errorResponse: sendError, ok, notFound } = require('../src/utils/responses');
|
||||
const { ValidationError } = require('../src/utilities/errors');
|
||||
|
||||
/**
|
||||
* Health routes factory
|
||||
@@ -190,7 +190,7 @@ module.exports = function({
|
||||
|
||||
// Load service config
|
||||
if (!await exists(SERVICES_FILE)) {
|
||||
const { NotFoundError } = require('../errors');
|
||||
const { NotFoundError } = require('../src/utilities/errors');
|
||||
throw new NotFoundError('Services file');
|
||||
}
|
||||
|
||||
@@ -199,7 +199,7 @@ module.exports = function({
|
||||
const service = services.find(s => (s.id || s.name?.toLowerCase()) === serviceId);
|
||||
|
||||
if (!service) {
|
||||
const { NotFoundError } = require('../errors');
|
||||
const { NotFoundError } = require('../src/utilities/errors');
|
||||
throw new NotFoundError('Service');
|
||||
}
|
||||
|
||||
@@ -273,11 +273,7 @@ module.exports = function({
|
||||
try {
|
||||
// Check if certificate exists
|
||||
if (!await exists(rootCertPath)) {
|
||||
return res.json({
|
||||
status: 'error',
|
||||
message: 'Root CA certificate not found',
|
||||
daysUntilExpiration: null
|
||||
});
|
||||
return sendError(res, 404, 'Root CA certificate not found', { caStatus: 'error', daysUntilExpiration: null });
|
||||
}
|
||||
|
||||
const dates = execSync(`openssl x509 -in "${rootCertPath}" -noout -dates`).toString();
|
||||
@@ -286,36 +282,32 @@ module.exports = function({
|
||||
const daysUntilExpiration = Math.floor((expirationDate - new Date()) / (1000 * 60 * 60 * 24));
|
||||
|
||||
// Alert thresholds
|
||||
let status = 'healthy';
|
||||
let caStatus = 'healthy';
|
||||
let message = `CA certificate valid for ${daysUntilExpiration} days`;
|
||||
|
||||
if (daysUntilExpiration < 0) {
|
||||
status = 'critical';
|
||||
caStatus = 'critical';
|
||||
message = `CA certificate EXPIRED ${Math.abs(daysUntilExpiration)} days ago!`;
|
||||
} else if (daysUntilExpiration < 7) {
|
||||
status = 'critical';
|
||||
caStatus = 'critical';
|
||||
message = `CA certificate expires in ${daysUntilExpiration} days!`;
|
||||
} else if (daysUntilExpiration < 30) {
|
||||
status = 'critical';
|
||||
caStatus = 'critical';
|
||||
message = `CA certificate expires in ${daysUntilExpiration} days!`;
|
||||
} else if (daysUntilExpiration < 90) {
|
||||
status = 'warning';
|
||||
caStatus = 'warning';
|
||||
message = `CA certificate expires in ${daysUntilExpiration} days`;
|
||||
}
|
||||
|
||||
res.json({
|
||||
status: status,
|
||||
message: message,
|
||||
daysUntilExpiration: daysUntilExpiration,
|
||||
ok(res, {
|
||||
caStatus,
|
||||
message,
|
||||
daysUntilExpiration,
|
||||
expiresAt: notAfter
|
||||
});
|
||||
} catch (error) {
|
||||
await logError('GET /api/health/ca', error);
|
||||
res.json({
|
||||
status: 'error',
|
||||
message: error.message,
|
||||
daysUntilExpiration: null
|
||||
});
|
||||
sendError(res, 500, error.message, { caStatus: 'error', daysUntilExpiration: null });
|
||||
}
|
||||
}, 'health-ca'));
|
||||
|
||||
@@ -349,7 +341,7 @@ module.exports = function({
|
||||
const hours = parseInt(req.query.hours) || 24;
|
||||
const stats = healthChecker.getServiceStats(req.params.serviceId, hours);
|
||||
if (!stats) {
|
||||
const { NotFoundError } = require('../errors');
|
||||
const { NotFoundError } = require('../src/utilities/errors');
|
||||
throw new NotFoundError('Service');
|
||||
}
|
||||
success(res, { stats });
|
||||
|
||||
Reference in New Issue
Block a user