From befbc024c9aead7fd600bae6c84af691ead1ff8c Mon Sep 17 00:00:00 2001 From: Kaoru0822 Date: Thu, 15 Oct 2026 05:21:17 -0700 Subject: [PATCH] fix(apple): select only entries named Assets.car as asset catalogs (#4094) inspect-asset-catalog selected every bundle entry whose relative path ended in Assets.car, so an unrelated NotAssets.car directory was listed as a skipped catalog and, with no real catalog present, failed the inspection instead of returning the empty inventory; a regular file such as OldAssets.car would have been sent to assetutil. The selector now compares the final path component exactly. Fixes #3914 Co-authored-by: Claude Opus 5.5 --- src/artifacts/apple/AppleAssetCatalogAnalysis.test.ts | 3 +++ src/artifacts/apple/AppleAssetCatalogAnalysis.ts | 4 +++- 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/src/artifacts/apple/AppleAssetCatalogAnalysis.test.ts b/src/artifacts/apple/AppleAssetCatalogAnalysis.test.ts index 5b35d7955e..88af6ce4da 100644 --- a/src/artifacts/apple/AppleAssetCatalogAnalysis.test.ts +++ b/src/artifacts/apple/AppleAssetCatalogAnalysis.test.ts @@ -68,6 +68,9 @@ describe("Apple asset catalog application workflow", () => { const bundle = await createTestTempDirectory("rea-asset-catalog-absent-"); await mkdir(join(bundle, "Contents", "Resources"), { recursive: true }); await writeFile(join(bundle, "Contents", "Resources", "icon.icns"), ""); + // Names that merely end in Assets.car are ordinary resources. + await mkdir(join(bundle, "Contents", "Resources", "NotAssets.car")); + await writeFile(join(bundle, "Contents", "Resources", "OldAssets.car"), ""); const result = await analyzeAppleAssetCatalogs({ environment: {}, bundlePath: bundle, diff --git a/src/artifacts/apple/AppleAssetCatalogAnalysis.ts b/src/artifacts/apple/AppleAssetCatalogAnalysis.ts index 262f63d70e..84809ec08b 100644 --- a/src/artifacts/apple/AppleAssetCatalogAnalysis.ts +++ b/src/artifacts/apple/AppleAssetCatalogAnalysis.ts @@ -122,7 +122,9 @@ const collectAssetCatalogs = async (input: { let totalMetadataBytes = 0; try { for await (const entry of reader.entries(input.signal)) { - if (!entry.path.endsWith("Assets.car")) continue; + // Reader paths are `/`-separated; only an entry named exactly + // Assets.car is a compiled catalog, not e.g. NotAssets.car. + if (entry.path.split("/").at(-1) !== "Assets.car") continue; if (entry.kind !== "file") { uninspected.push(`${entry.path} (${entry.kind})`); continue;