From 64ae9c02ea24a55c7a659ea52922a99e2124380b Mon Sep 17 00:00:00 2001 From: Arnav Date: Tue, 27 Oct 2026 19:35:41 +0530 Subject: [PATCH] fix(scripts): normalize Windows path separators in validation scripts --- scripts/check-api-validation-contracts.ts | 35 ++++++++++++----------- scripts/check-tool-registry-boundary.ts | 2 +- 2 files changed, 19 insertions(+), 18 deletions(-) diff --git a/scripts/check-api-validation-contracts.ts b/scripts/check-api-validation-contracts.ts index 71be84f6021..dff96c7022f 100644 --- a/scripts/check-api-validation-contracts.ts +++ b/scripts/check-api-validation-contracts.ts @@ -3,10 +3,11 @@ import { readdir, readFile } from 'node:fs/promises' import path from 'node:path' const ROOT = path.resolve(import.meta.dir, '..') -const API_DIR = path.join(ROOT, 'apps/sim/app/api') -const CONTRACTS_DIR = path.join(ROOT, 'apps/sim/lib/api/contracts') -const QUERY_HOOKS_DIR = path.join(ROOT, 'apps/sim/hooks/queries') -const SELECTOR_HOOKS_DIR = path.join(ROOT, 'apps/sim/hooks/selectors') +const toPosix = (p: string) => p.replace(/\\/g, '/') +const API_DIR = toPosix(path.join(ROOT, 'apps/sim/app/api')) +const CONTRACTS_DIR = toPosix(path.join(ROOT, 'apps/sim/lib/api/contracts')) +const QUERY_HOOKS_DIR = toPosix(path.join(ROOT, 'apps/sim/hooks/queries')) +const SELECTOR_HOOKS_DIR = toPosix(path.join(ROOT, 'apps/sim/hooks/selectors')) /** * `totalRoutes` is reported, never gated. @@ -477,7 +478,7 @@ function findRawFetchFindings( exemptions: number missingReasons: AnnotationMissingReasonFinding[] } { - const relativePath = path.relative(ROOT, filePath) + const relativePath = toPosix(path.relative(ROOT, filePath)) const lines = content.split('\n') const findings: RawFetchFinding[] = [] const missingReasons: AnnotationMissingReasonFinding[] = [] @@ -515,7 +516,7 @@ function findDoubleCastFindings( exemptions: number missingReasons: AnnotationMissingReasonFinding[] } { - const relativePath = path.relative(ROOT, filePath) + const relativePath = toPosix(path.relative(ROOT, filePath)) const lines = content.split('\n') const findings: DoubleCastFinding[] = [] const missingReasons: AnnotationMissingReasonFinding[] = [] @@ -562,7 +563,7 @@ function findRawJsonFindings( exemptions: number missingReasons: AnnotationMissingReasonFinding[] } { - const relativePath = path.relative(ROOT, filePath) + const relativePath = toPosix(path.relative(ROOT, filePath)) const lines = content.split('\n') const findings: RawJsonFinding[] = [] const missingReasons: AnnotationMissingReasonFinding[] = [] @@ -613,7 +614,7 @@ function findUntypedResponseFindings( exemptions: number missingReasons: AnnotationMissingReasonFinding[] } { - const relativePath = path.relative(ROOT, filePath) + const relativePath = toPosix(path.relative(ROOT, filePath)) const lines = content.split('\n') const findings: UntypedResponseFinding[] = [] const missingReasons: AnnotationMissingReasonFinding[] = [] @@ -683,7 +684,7 @@ function findSameOriginApiFetchFindings( exemptions: number missingReasons: AnnotationMissingReasonFinding[] } { - const relativePath = path.relative(ROOT, filePath) + const relativePath = toPosix(path.relative(ROOT, filePath)) const lines = content.split('\n') const findings: SameOriginApiFetchFinding[] = [] const missingReasons: AnnotationMissingReasonFinding[] = [] @@ -713,7 +714,7 @@ function findSameOriginApiFetchFindings( } function routeFamily(routePath: string): string { - const relative = routePath.replace(/^apps\/sim\/app\/api\//, '') + const relative = toPosix(routePath).replace(/^apps\/sim\/app\/api\//, '') const [first, second] = relative.split('/') if (first === 'tools') return `tools/${second ?? 'unknown'}` @@ -767,7 +768,7 @@ function hasZodUsage(relativePath: string, content: string): boolean { } function auditRoute(filePath: string, content: string): RouteAudit { - const relativePath = path.relative(ROOT, filePath) + const relativePath = toPosix(path.relative(ROOT, filePath)) const schemaConstructorCount = [...content.matchAll(ZOD_SCHEMA_CONSTRUCTOR_PATTERN)].length return { @@ -785,7 +786,7 @@ function auditRoute(filePath: string, content: string): RouteAudit { function findAdHocWireTypes(filePath: string, content: string): WireTypeFinding[] { const findings: WireTypeFinding[] = [] - const relativePath = path.relative(ROOT, filePath) + const relativePath = toPosix(path.relative(ROOT, filePath)) for (const match of content.matchAll(WIRE_TYPE_DECLARATION_PATTERN)) { const kind = match[1] @@ -814,7 +815,7 @@ function findAdHocWireTypes(filePath: string, content: string): WireTypeFinding[ } function auditQueryHook(filePath: string, content: string): QueryHookAudit { - const relativePath = path.relative(ROOT, filePath) + const relativePath = toPosix(path.relative(ROOT, filePath)) const schemaConstructorCount = [...content.matchAll(ZOD_SCHEMA_CONSTRUCTOR_PATTERN)].length return { @@ -1281,13 +1282,13 @@ async function main() { let sameOriginApiFetchExemptions = 0 let doubleCastExemptions = 0 - const appsSimRoot = path.join(ROOT, 'apps/sim') - const contractsRoot = path.join(CONTRACTS_DIR, path.sep) + const appsSimRoot = toPosix(path.join(ROOT, 'apps/sim')) + const contractsRoot = `${toPosix(CONTRACTS_DIR)}/` for (const filePath of sourceFiles) { const content = sourceCache.get(filePath) ?? (await readFile(filePath, 'utf8')) - if (filePath.startsWith(contractsRoot)) sourceCache.set(filePath, content) - const normalized = filePath.replace(/\\/g, '/') + const normalized = toPosix(filePath) + if (normalized.startsWith(contractsRoot)) sourceCache.set(filePath, content) if (isClientHookFile(filePath) && content.includes('fetch')) { const rawFetch = findRawFetchFindings(filePath, content) diff --git a/scripts/check-tool-registry-boundary.ts b/scripts/check-tool-registry-boundary.ts index 41467280b63..62188738252 100644 --- a/scripts/check-tool-registry-boundary.ts +++ b/scripts/check-tool-registry-boundary.ts @@ -169,7 +169,7 @@ function collectEntries( for (const entry of readdirSync(dir, { withFileTypes: true })) { const full = join(dir, entry.name) if (entry.isDirectory()) collectEntries(full, matches, found) - else if (matches(entry.name, full)) found.push(relative(APP, full)) + else if (matches(entry.name, full)) found.push(relative(APP, full).replaceAll('\\', '/')) } return found }