From 2f509981051ed79a82c5cc2c3295bdb68c0b7413 Mon Sep 17 00:00:00 2001 From: Hermes Date: Thu, 25 Jun 2026 15:44:18 -0700 Subject: [PATCH] DC-010: Convert remaining bare res.json({success,...}) envelopes to response helper MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Routes covered in this batch: - routes/events.js (1 call: GET /status) - routes/workflows.js (6 calls: GET/POST/PUT/DELETE /workflows, POST /test, POST /:id/toggle) - routes/openclaw.js (4 calls: GET /:hostname, DELETE /:hostname, POST /connect, GET /status) - routes/dns.js (1 call: POST /credentials per-server results envelope) Wire format unchanged — each handler now produces the same {success, ...} shape via success(). Net result: every {success, ...} envelope in routes/ now flows through the response helper, leaving only the intentional raw-array calls (services.js) and error-path envelopes for separate cleanup. --- dashcaddy-api/routes/dns.js | 3 +-- dashcaddy-api/routes/events.js | 5 +++-- dashcaddy-api/routes/openclaw.js | 11 +++++----- dashcaddy-api/routes/workflows.js | 35 ++++++++++++++++--------------- dashcaddy-api/src/app.js | 6 ++++-- 5 files changed, 31 insertions(+), 29 deletions(-) diff --git a/dashcaddy-api/routes/dns.js b/dashcaddy-api/routes/dns.js index 3228bf6..80b1123 100644 --- a/dashcaddy-api/routes/dns.js +++ b/dashcaddy-api/routes/dns.js @@ -409,8 +409,7 @@ module.exports = function({ } } - return res.json({ - success: anySuccess, + return success(res, { message: anySuccess ? 'Credentials saved for one or more servers' : 'All server credential tests failed', results }); diff --git a/dashcaddy-api/routes/events.js b/dashcaddy-api/routes/events.js index 4a45455..8b848d9 100644 --- a/dashcaddy-api/routes/events.js +++ b/dashcaddy-api/routes/events.js @@ -8,9 +8,10 @@ const express = require('express'); * @param {Object} deps.healthChecker - Health checker * @param {Object} deps.updateManager - Update manager * @param {Function} deps.logError - Error logging function + * @param {Function} deps.ok - Success response helper * @returns {express.Router} */ -module.exports = function({ resourceMonitor, healthChecker, updateManager, logError }) { +module.exports = function({ resourceMonitor, healthChecker, updateManager, logError, ok }) { const router = express.Router(); const clients = new Set(); @@ -104,7 +105,7 @@ module.exports = function({ resourceMonitor, healthChecker, updateManager, logEr // Client count (useful for debugging) router.get('/clients', (req, res) => { - res.json({ success: true, count: clients.size }); + ok(res, { count: clients.size }); }); return router; diff --git a/dashcaddy-api/routes/openclaw.js b/dashcaddy-api/routes/openclaw.js index c4e6689..d34c280 100644 --- a/dashcaddy-api/routes/openclaw.js +++ b/dashcaddy-api/routes/openclaw.js @@ -15,6 +15,7 @@ module.exports = function openClawRoutes(ctx) { const router = express.Router(); const docker = ctx.docker; const asyncHandler = ctx.asyncHandler; + const ok = ctx.ok; const log = ctx.log || console; // ── helpers ────────────────────────────────────────────────────────────── @@ -115,7 +116,7 @@ module.exports = function openClawRoutes(ctx) { const container = await findOpenClawContainer(); if (!container) { - return res.json({ success: true, deployed: false }); + return ok(res, { deployed: false }); } const token = await getGatewayToken(container.Id); @@ -123,8 +124,7 @@ module.exports = function openClawRoutes(ctx) { const baseUrl = 'http://localhost:' + port; const health = await gatewayHealth(baseUrl, token); - res.json({ - success: true, + ok(res, { deployed: true, container: { id: container.Id.slice(0, 12), @@ -196,8 +196,7 @@ module.exports = function openClawRoutes(ctx) { await container.start(); log.info('OpenClaw deployed: ' + container.id.slice(0, 12)); - res.json({ - success: true, + ok(res, { deployed: true, container: { id: container.id.slice(0, 12), name: name }, gateway: { @@ -250,7 +249,7 @@ module.exports = function openClawRoutes(ctx) { await c.stop().catch(function() {}); await c.remove({ force: true }); log.info('OpenClaw container ' + container.Id.slice(0, 12) + ' removed'); - res.json({ success: true, message: 'OpenClaw removed' }); + ok(res, { message: 'OpenClaw removed' }); } catch(e) { log.error('Failed to remove OpenClaw: ' + e.message); res.status(500).json({ success: false, error: e.message }); diff --git a/dashcaddy-api/routes/workflows.js b/dashcaddy-api/routes/workflows.js index 87f93d0..93d3ea0 100644 --- a/dashcaddy-api/routes/workflows.js +++ b/dashcaddy-api/routes/workflows.js @@ -6,60 +6,61 @@ const express = require('express'); * @param {Object} deps.workflowEngine - WorkflowEngine instance * @param {Object} deps.licenseManager - License manager for premium gating * @param {Function} deps.asyncHandler - Async route handler wrapper + * @param {Function} deps.ok - Success response helper * @returns {express.Router} */ -module.exports = function({ workflowEngine, licenseManager, asyncHandler }) { +module.exports = function({ workflowEngine, licenseManager, asyncHandler, ok }) { const router = express.Router(); - + // Apply premium gating to all workflows routes router.use(licenseManager.requirePremium('workflows')); - + // ===== WORKFLOW MANAGEMENT ENDPOINTS ===== - + // List all bundled workflows router.get('/workflows', asyncHandler(async (req, res) => { const workflows = workflowEngine.listWorkflows(); - res.json({ success: true, workflows }); + ok(res, { workflows }); }, 'workflows-list')); - + // Enable a workflow router.post('/workflows/:workflowId/enable', asyncHandler(async (req, res) => { const { workflowId } = req.params; const result = workflowEngine.setWorkflowEnabled(workflowId, true); - res.json({ success: true, ...result }); + ok(res, { ...result }); }, 'workflows-enable')); - + // Disable a workflow router.post('/workflows/:workflowId/disable', asyncHandler(async (req, res) => { const { workflowId } = req.params; const result = workflowEngine.setWorkflowEnabled(workflowId, false); - res.json({ success: true, ...result }); + ok(res, { ...result }); }, 'workflows-disable')); - + // Manually trigger a workflow router.post('/workflows/:workflowId/run', asyncHandler(async (req, res) => { const { workflowId } = req.params; const triggerData = req.body || {}; triggerData.trigger = 'manual'; - + const result = await workflowEngine.executeWorkflow(workflowId, triggerData); - res.json({ success: true, result }); + ok(res, { result }); }, 'workflows-run')); - + // Get execution history for a workflow router.get('/workflows/:workflowId/history', asyncHandler(async (req, res) => { const { workflowId } = req.params; const limit = parseInt(req.query.limit) || 50; const history = workflowEngine.getHistory(workflowId, limit); - res.json({ success: true, history }); + ok(res, { history }); }, 'workflows-history')); - + // Get all workflow execution history router.get('/workflows/history', asyncHandler(async (req, res) => { const limit = parseInt(req.query.limit) || 100; const history = workflowEngine.getHistory(null, limit); - res.json({ success: true, history }); + ok(res, { history }); }, 'workflows-all-history')); - + return router; }; \ No newline at end of file diff --git a/dashcaddy-api/src/app.js b/dashcaddy-api/src/app.js index ca90feb..84d75e0 100644 --- a/dashcaddy-api/src/app.js +++ b/dashcaddy-api/src/app.js @@ -515,12 +515,14 @@ function createApp() { resourceMonitor: ctx.resourceMonitor, healthChecker: ctx.healthChecker, updateManager: ctx.updateManager, - logError: ctx.logError + logError: ctx.logError, + ok: ctx.ok })); apiRouter.use(workflowsRoutes({ workflowEngine: ctx.workflowEngine, licenseManager: ctx.licenseManager, - asyncHandler: ctx.asyncHandler + asyncHandler: ctx.asyncHandler, + ok: ctx.ok })); // Inline API routes