diff --git a/server/routers/newt/targets.ts b/server/routers/newt/targets.ts index 25b520854..5c717fa94 100644 --- a/server/routers/newt/targets.ts +++ b/server/routers/newt/targets.ts @@ -28,36 +28,18 @@ export async function addTargets( { incrementConfigVersion: true, compress: canCompress(version, "newt") } ); - // Create a map for quick lookup - const healthCheckMap = new Map(); - healthCheckData.forEach((hc) => { - if (hc.targetId !== null) { - healthCheckMap.set(hc.targetId, hc); - } - }); - - const healthCheckTargets = targets.map((target) => { - const hc = healthCheckMap.get(target.targetId); - - // If no health check data found, skip this target - if (!hc) { - logger.warn( - `No health check configuration found for target ${target.targetId}` - ); - return null; - } - + const healthCheckTargets = healthCheckData.map((hc) => { // Ensure all necessary fields are present const isTCP = hc.hcMode?.toLowerCase() === "tcp"; if (!hc.hcHostname || !hc.hcPort || !hc.hcInterval) { logger.debug( - `Skipping target ${target.targetId} due to missing health check fields` + `Skipping hc ${hc.targetHealthCheckId} due to missing health check fields` ); return null; } if (!isTCP && (!hc.hcPath || !hc.hcMethod)) { logger.debug( - `Skipping target ${target.targetId} due to missing HTTP health check fields` + `Skipping hc ${hc.targetHealthCheckId} due to missing HTTP health check fields` ); return null; } @@ -105,7 +87,7 @@ export async function addTargets( // Filter out any null values from health check targets const validHealthCheckTargets = healthCheckTargets.filter( - (target) => target !== null + (hc) => hc !== null ); await sendToClient( @@ -213,6 +195,7 @@ export async function removeStandaloneHealthCheck( export async function removeTargets( newtId: string, targets: Target[], + healthCheckData: TargetHealthCheck[], protocol: string, version?: string | null ) { @@ -234,8 +217,8 @@ export async function removeTargets( { incrementConfigVersion: true } ); - const healthCheckTargets = targets.map((target) => { - return target.targetId; + const healthCheckTargets = healthCheckData.map((hc) => { + return hc.targetHealthCheckId; }); await sendToClient( diff --git a/server/routers/resource/deleteResource.ts b/server/routers/resource/deleteResource.ts index e63301867..b29f7732d 100644 --- a/server/routers/resource/deleteResource.ts +++ b/server/routers/resource/deleteResource.ts @@ -1,8 +1,8 @@ import { Request, Response, NextFunction } from "express"; import { z } from "zod"; -import { db } from "@server/db"; +import { db, targetHealthCheck } from "@server/db"; import { newts, resources, sites, targets } from "@server/db"; -import { eq } from "drizzle-orm"; +import { eq, inArray } from "drizzle-orm"; import response from "@server/lib/response"; import HttpCode from "@server/types/HttpCode"; import createHttpError from "http-errors"; @@ -52,6 +52,16 @@ export async function deleteResource( .from(targets) .where(eq(targets.resourceId, resourceId)); + const targetHealthChecksToBeRemoved = await db + .select() + .from(targetHealthCheck) + .where( + inArray( + targetHealthCheck.targetId, + targetsToBeRemoved.map((t) => t.targetId) + ) + ); + const [deletedResource] = await db .delete(resources) .where(eq(resources.resourceId, resourceId)) @@ -66,44 +76,40 @@ export async function deleteResource( ); } - // const [site] = await db - // .select() - // .from(sites) - // .where(eq(sites.siteId, deletedResource.siteId!)) - // .limit(1); - // - // if (!site) { - // return next( - // createHttpError( - // HttpCode.NOT_FOUND, - // `Site with ID ${deletedResource.siteId} not found` - // ) - // ); - // } - // - // if (site.pubKey) { - // if (site.type == "wireguard") { - // await addPeer(site.exitNodeId!, { - // publicKey: site.pubKey, - // allowedIps: await getAllowedIps(site.siteId) - // }); - // } else if (site.type == "newt") { - // // get the newt on the site by querying the newt table for siteId - // const [newt] = await db - // .select() - // .from(newts) - // .where(eq(newts.siteId, site.siteId)) - // .limit(1); - // - // removeTargets( - // newt.newtId, - // targetsToBeRemoved, - // deletedResource.protocol, - // deletedResource.proxyPort - // ); - // } - // } - // + const [site] = await db + .select() + .from(sites) + .where(eq(sites.siteId, targets.siteId)) + .limit(1); + + if (!site) { + return next( + createHttpError( + HttpCode.NOT_FOUND, + `Site with ID ${targets.siteId} not found` + ) + ); + } + + if (site.pubKey) { + if (site.type == "newt") { + // get the newt on the site by querying the newt table for siteId + const [newt] = await db + .select() + .from(newts) + .where(eq(newts.siteId, site.siteId)) + .limit(1); + + await removeTargets( + newt.newtId, + targetsToBeRemoved, + targetHealthChecksToBeRemoved, + deletedResource.protocol, + newt.version + ); + } + } + return response(res, { data: null, success: true, diff --git a/server/routers/target/deleteTarget.ts b/server/routers/target/deleteTarget.ts index 606d86351..754a047ff 100644 --- a/server/routers/target/deleteTarget.ts +++ b/server/routers/target/deleteTarget.ts @@ -12,6 +12,7 @@ import { fromError } from "zod-validation-error"; import { removeTargets } from "../newt/targets"; import { getAllowedIps } from "./helpers"; import { OpenAPITags, registry } from "@server/openApi"; +import { targetHealthCheck } from "@server/db/pg"; const deleteTargetSchema = z.strictObject({ targetId: z.string().transform(Number).pipe(z.int().positive()) @@ -46,6 +47,11 @@ export async function deleteTarget( const { targetId } = parsedParams.data; + const [deletedHealthCheck] = await db + .delete(targetHealthCheck) + .where(eq(targetHealthCheck.targetId, targetId)) + .returning(); + const [deletedTarget] = await db .delete(targets) .where(eq(targets.targetId, targetId)) @@ -74,38 +80,39 @@ export async function deleteTarget( ); } - // const [site] = await db - // .select() - // .from(sites) - // .where(eq(sites.siteId, resource.siteId!)) - // .limit(1); - // - // if (!site) { - // return next( - // createHttpError( - // HttpCode.NOT_FOUND, - // `Site with ID ${resource.siteId} not found` - // ) - // ); - // } - // - // if (site.pubKey) { - // if (site.type == "wireguard") { - // await addPeer(site.exitNodeId!, { - // publicKey: site.pubKey, - // allowedIps: await getAllowedIps(site.siteId) - // }); - // } else if (site.type == "newt") { - // // get the newt on the site by querying the newt table for siteId - // const [newt] = await db - // .select() - // .from(newts) - // .where(eq(newts.siteId, site.siteId)) - // .limit(1); - // - // removeTargets(newt.newtId, [deletedTarget], resource.protocol, resource.proxyPort); - // } - // } + const [site] = await db + .select() + .from(sites) + .where(eq(sites.siteId, targets.siteId)) + .limit(1); + + if (!site) { + return next( + createHttpError( + HttpCode.NOT_FOUND, + `Site with ID ${targets.siteId} not found` + ) + ); + } + + if (site.pubKey) { + if (site.type == "newt") { + // get the newt on the site by querying the newt table for siteId + const [newt] = await db + .select() + .from(newts) + .where(eq(newts.siteId, site.siteId)) + .limit(1); + + await removeTargets( + newt.newtId, + [deletedTarget], + [deletedHealthCheck], + resource.protocol, + newt.version + ); + } + } return response(res, { data: null,