import type { Application, RequestHandler, Response } from "express"; import { Router } from "express"; import { z } from "zod/v4"; import { InventoryParamsSchema, ResourceParamsSchema, SaveResourceRequestSchema, SetResourceActiveRequestSchema, } from "../../../common/inventory"; import { diagnoseNetworkShares } from "../../application/network-share-diagnostics"; import type { ResourceUseCases } from "../../application/resource.use-cases"; import { buildResourceResponse } from "../../application/resource-response.builder"; const LifecycleRequestSchema = z.discriminatedUnion("action", [ z.strictObject({ action: z.literal("status"), body: SetResourceActiveRequestSchema }), z.strictObject({ action: z.literal("delete"), body: z.strictObject({}) }), ]); function fail(response: Response, code: string) { response .status(code === "INVALID_REQUEST" ? 400 : code.endsWith("NOT_FOUND") ? 404 : 409) .json({ code, requestId: response.getHeader("x-request-id") }); } function sendResource( response: Response, result: Awaited> ) { if (!result.isSuccess) { fail(response, result.error.code); return; } response.json({ resource: buildResourceResponse( result.data.resource, result.data.actorNames, result.data.directory, result.data.networkShare ), }); } function sendDeleted(response: Response, result: Awaited>) { if (!result.isSuccess) { fail(response, result.error.code); return; } response.json({ deleted: true }); } export function registerResourceRoutes( app: Application, useCases: ResourceUseCases, authenticate: RequestHandler ) { const router = Router(); for (const action of ["status", "delete"] as const) { router.post(`/:companyId/:id/${action}`, (request, response, next) => { const params = ResourceParamsSchema.safeParse(request.params); const actor = z .object({ userId: z.uuid() }) .safeParse("session" in request ? request.session : undefined); const body = LifecycleRequestSchema.safeParse({ action, body: request.body }); if ( !( params.success && actor.success && body.success && z.strictObject({}).safeParse(request.query).success ) ) { fail(response, "INVALID_REQUEST"); return; } if (body.data.action === "delete") { useCases .remove(params.data.companyId, params.data.id) .then((result) => sendDeleted(response, result)) .catch(next); return; } useCases .setActive(params.data.companyId, params.data.id, body.data.body.active, actor.data.userId) .then((result) => sendResource(response, result)) .catch(next); }); } router.get("/:companyId/network-share-diagnostics", (request, response, next) => { const params = InventoryParamsSchema.safeParse(request.params); if (!(params.success && z.strictObject({}).safeParse(request.query).success)) { fail(response, "INVALID_REQUEST"); return; } useCases .get(params.data.companyId) .then((result) => { if (!result.isSuccess) { fail(response, result.error.code); return; } response.json({ items: diagnoseNetworkShares(result.data) }); }) .catch(next); }); router.get("/:companyId", (request, response, next) => { const params = InventoryParamsSchema.safeParse(request.params); const query = z.strictObject({ environmentId: z.uuid().optional() }).safeParse(request.query); if (!(params.success && query.success)) { fail(response, "INVALID_REQUEST"); return; } useCases .get(params.data.companyId) .then((result) => { if (!result.isSuccess) { fail(response, result.error.code); return; } response.json({ references: result.data.references, resources: result.data.resources .filter( (resource) => !query.data.environmentId || result.data.directoryDomains?.get(resource.id.toPrimitive())?.environmentId === query.data.environmentId.toLowerCase() ) .map((resource) => buildResourceResponse( resource, result.data.actorNames, result.data.directoryDomains?.get(resource.id.toPrimitive()), result.data.networkShares?.get(resource.id.toPrimitive()) ) ), }); }) .catch(next); }); for (const path of ["/:companyId", "/:companyId/:id/update"]) { router.post(path, (request, response, next) => { const params = ( path.endsWith("update") ? ResourceParamsSchema : InventoryParamsSchema ).safeParse(request.params); const body = SaveResourceRequestSchema.safeParse(request.body); const actor = z .object({ userId: z.uuid() }) .safeParse("session" in request ? request.session : undefined); if (!(params.success && body.success && actor.success)) { fail(response, "INVALID_REQUEST"); return; } const id = "id" in params.data && typeof params.data.id === "string" ? params.data.id : undefined; useCases .save(params.data.companyId, id, body.data.values, actor.data.userId) .then((result) => { if (!result.isSuccess) { fail(response, result.error.code); return; } response.status(id ? 200 : 201).json({ resource: buildResourceResponse( result.data.resource, result.data.actorNames, result.data.directory, result.data.networkShare ), }); }) .catch(next); }); } app.use("/api/resources", authenticate, router); }