Merge pull request #3085 from marcschaeferger-org/security-updates

Normalize request parameters and update dependencies for Security
This commit is contained in:
Owen Schwartz
2026-05-27 21:37:50 -07:00
committed by Owen
parent ddabfb5ca1
commit 2946df3b8e
37 changed files with 2656 additions and 3609 deletions

View File

@@ -19,6 +19,7 @@ import { eq, and } from "drizzle-orm";
import createHttpError from "http-errors";
import HttpCode from "@server/types/HttpCode";
import logger from "@server/logger";
import { getFirstString } from "@server/lib/requestParams";
export async function verifyCertificateAccess(
req: Request,
@@ -27,11 +28,43 @@ export async function verifyCertificateAccess(
) {
try {
// Assume user/org access is already verified
const orgId = req.params.orgId;
const certId =
req.params.certId || req.body?.certId || req.query?.certId;
let domainId =
req.params.domainId || req.body?.domainId || req.query?.domainId;
const orgId = getFirstString(req.params.orgId);
const certIdFromParams = getFirstString(req.params?.certId);
const certIdFromBody = getFirstString(req.body?.certId);
if (
certIdFromParams &&
certIdFromBody &&
certIdFromParams !== certIdFromBody
) {
return next(
createHttpError(
HttpCode.BAD_REQUEST,
"Certificate ID provided in both URL and body with different values"
)
);
}
const certId = certIdFromParams || certIdFromBody;
const domainIdFromParams = getFirstString(req.params?.domainId);
const domainIdFromBody = getFirstString(req.body?.domainId);
if (
domainIdFromParams &&
domainIdFromBody &&
domainIdFromParams !== domainIdFromBody
) {
return next(
createHttpError(
HttpCode.BAD_REQUEST,
"Domain ID provided in both URL and body with different values"
)
);
}
let domainId = domainIdFromParams || domainIdFromBody;
if (!orgId) {
return next(
@@ -65,7 +98,7 @@ export async function verifyCertificateAccess(
);
}
domainId = cert.domainId;
domainId = cert.domainId ?? undefined;
if (!domainId) {
return next(
createHttpError(

View File

@@ -17,6 +17,7 @@ import { and, eq } from "drizzle-orm";
import createHttpError from "http-errors";
import HttpCode from "@server/types/HttpCode";
import { getUserOrgRoleIds } from "@server/lib/userOrgRoles";
import { getFirstString } from "@server/lib/requestParams";
export async function verifyIdpAccess(
req: Request,
@@ -25,8 +26,12 @@ export async function verifyIdpAccess(
) {
try {
const userId = req.user!.userId;
const idpId = req.params.idpId || req.body.idpId || req.query.idpId;
const orgId = req.params.orgId;
const idpIdRaw =
getFirstString(req.params.idpId) ||
getFirstString(req.body?.idpId) ||
getFirstString(req.query?.idpId);
const idpId = Number.parseInt(idpIdRaw ?? "", 10);
const orgId = getFirstString(req.params.orgId);
if (!userId) {
return next(
@@ -40,7 +45,7 @@ export async function verifyIdpAccess(
);
}
if (!idpId) {
if (Number.isNaN(idpId)) {
return next(
createHttpError(HttpCode.BAD_REQUEST, "Invalid key ID")
);

View File

@@ -18,6 +18,7 @@ import { and, eq } from "drizzle-orm";
import createHttpError from "http-errors";
import HttpCode from "@server/types/HttpCode";
import { getUserOrgRoleIds } from "@server/lib/userOrgRoles";
import { getFirstString } from "@server/lib/requestParams";
export async function verifyRemoteExitNodeAccess(
req: Request,
@@ -25,11 +26,11 @@ export async function verifyRemoteExitNodeAccess(
next: NextFunction
) {
const userId = req.user!.userId; // Assuming you have user information in the request
const orgId = req.params.orgId;
const orgId = getFirstString(req.params.orgId);
const remoteExitNodeId =
req.params.remoteExitNodeId ||
req.body.remoteExitNodeId ||
req.query.remoteExitNodeId;
getFirstString(req.params.remoteExitNodeId) ||
getFirstString(req.body?.remoteExitNodeId) ||
getFirstString(req.query?.remoteExitNodeId);
if (!userId) {
return next(
@@ -37,6 +38,15 @@ export async function verifyRemoteExitNodeAccess(
);
}
if (!orgId || !remoteExitNodeId) {
return next(
createHttpError(
HttpCode.BAD_REQUEST,
"Invalid organization or remote exit node ID"
)
);
}
try {
const [remoteExitNode] = await db
.select()

View File

@@ -16,40 +16,44 @@ import HttpCode from "@server/types/HttpCode";
import createHttpError from "http-errors";
import logger from "@server/logger";
import { response as sendResponse } from "@server/lib/response";
import { getFirstString } from "@server/lib/requestParams";
import privateConfig from "#private/lib/config";
import { GenerateNewLicenseResponse } from "@server/routers/generatedLicense/types";
export interface CreateNewLicenseResponse {
data: Data
success: boolean
error: boolean
message: string
status: number
data: Data;
success: boolean;
error: boolean;
message: string;
status: number;
}
export interface Data {
licenseKey: LicenseKey
licenseKey: LicenseKey;
}
export interface LicenseKey {
id: number
instanceName: any
instanceId: string
licenseKey: string
tier: string
type: string
quantity: number
quantity_2: number
isValid: boolean
updatedAt: string
createdAt: string
expiresAt: string
paidFor: boolean
orgId: string
metadata: string
id: number;
instanceName: any;
instanceId: string;
licenseKey: string;
tier: string;
type: string;
quantity: number;
quantity_2: number;
isValid: boolean;
updatedAt: string;
createdAt: string;
expiresAt: string;
paidFor: boolean;
orgId: string;
metadata: string;
}
export async function createNewLicense(orgId: string, licenseData: any): Promise<CreateNewLicenseResponse> {
export async function createNewLicense(
orgId: string,
licenseData: any
): Promise<CreateNewLicenseResponse> {
try {
const response = await fetch(
`${privateConfig.getRawPrivateConfig().server.fossorial_api}/api/v1/license-internal/enterprise/${orgId}/create`, // this says enterprise but it does both
@@ -80,7 +84,7 @@ export async function generateNewLicense(
next: NextFunction
): Promise<any> {
try {
const { orgId } = req.params;
const orgId = getFirstString(req.params.orgId);
if (!orgId) {
return next(

View File

@@ -16,6 +16,7 @@ import HttpCode from "@server/types/HttpCode";
import createHttpError from "http-errors";
import logger from "@server/logger";
import { response as sendResponse } from "@server/lib/response";
import { getFirstString } from "@server/lib/requestParams";
import privateConfig from "#private/lib/config";
import {
GeneratedLicenseKey,
@@ -55,7 +56,7 @@ export async function listSaasLicenseKeys(
next: NextFunction
): Promise<any> {
try {
const { orgId } = req.params;
const orgId = getFirstString(req.params.orgId);
if (!orgId) {
return next(