From ba68d19a74377b6c08345575dd450372aa2cc81b Mon Sep 17 00:00:00 2001 From: nicktrn <55853254+nicktrn@users.noreply.github.com> Date: Wed, 2 Jul 2025 17:10:28 +0100 Subject: [PATCH] track if repo created and fix test --- .../app/v3/getDeploymentImageRef.server.ts | 19 +++++-- .../services/initializeDeployment.server.ts | 3 +- .../webapp/test/getDeploymentImageRef.test.ts | 53 ++++++++++++++----- 3 files changed, 57 insertions(+), 18 deletions(-) diff --git a/apps/webapp/app/v3/getDeploymentImageRef.server.ts b/apps/webapp/app/v3/getDeploymentImageRef.server.ts index 2a3fd00ac..9a770cf15 100644 --- a/apps/webapp/app/v3/getDeploymentImageRef.server.ts +++ b/apps/webapp/app/v3/getDeploymentImageRef.server.ts @@ -113,6 +113,7 @@ export async function getDeploymentImageRef({ }): Promise<{ imageRef: string; isEcr: boolean; + repoCreated: boolean; }> { const repositoryName = `${namespace}/${projectRef}`; const imageRef = `${host}/${repositoryName}:${nextVersion}.${environmentSlug}`; @@ -121,10 +122,11 @@ export async function getDeploymentImageRef({ return { imageRef, isEcr: false, + repoCreated: false, }; } - const [ecrRepoError] = await tryCatch( + const [ecrRepoError, ecrData] = await tryCatch( ensureEcrRepositoryExists({ repositoryName, registryHost: host, @@ -145,6 +147,7 @@ export async function getDeploymentImageRef({ return { imageRef, isEcr: true, + repoCreated: ecrData.repoCreated, }; } @@ -157,7 +160,7 @@ export function isEcrRegistry(registryHost: string) { } } -function parseRegistryTags(tags: string): Tag[] { +export function parseRegistryTags(tags: string): Tag[] { if (!tags) { return []; } @@ -297,7 +300,7 @@ async function ensureEcrRepositoryExists({ registryHost: string; registryTags?: string; assumeRole?: AssumeRoleConfig; -}): Promise { +}): Promise<{ repo: Repository; repoCreated: boolean }> { const { region, accountId } = parseEcrRegistryDomain(registryHost); const [getRepoError, existingRepo] = await tryCatch( @@ -311,7 +314,10 @@ async function ensureEcrRepositoryExists({ if (existingRepo) { logger.debug("ECR repository already exists", { repositoryName, region, existingRepo }); - return existingRepo; + return { + repo: existingRepo, + repoCreated: false, + }; } const [createRepoError, newRepo] = await tryCatch( @@ -330,7 +336,10 @@ async function ensureEcrRepositoryExists({ ); } - return newRepo; + return { + repo: newRepo, + repoCreated: true, + }; } export async function getEcrAuthToken({ diff --git a/apps/webapp/app/v3/services/initializeDeployment.server.ts b/apps/webapp/app/v3/services/initializeDeployment.server.ts index 73965e5b5..6462c14c2 100644 --- a/apps/webapp/app/v3/services/initializeDeployment.server.ts +++ b/apps/webapp/app/v3/services/initializeDeployment.server.ts @@ -96,7 +96,7 @@ export class InitializeDeploymentService extends BaseService { throw new ServiceValidationError("Failed to get deployment image ref"); } - const { imageRef, isEcr } = imageRefResult; + const { imageRef, isEcr, repoCreated } = imageRefResult; logger.debug("Creating deployment", { environmentId: environment.id, @@ -106,6 +106,7 @@ export class InitializeDeploymentService extends BaseService { type: payload.type, imageRef, isEcr, + repoCreated, }); const deployment = await this._prisma.workerDeployment.create({ diff --git a/apps/webapp/test/getDeploymentImageRef.test.ts b/apps/webapp/test/getDeploymentImageRef.test.ts index b3b9ca571..01a04c53a 100644 --- a/apps/webapp/test/getDeploymentImageRef.test.ts +++ b/apps/webapp/test/getDeploymentImageRef.test.ts @@ -4,6 +4,7 @@ import { getDeploymentImageRef, getEcrAuthToken, parseEcrRegistryDomain, + parseRegistryTags, } from "../app/v3/getDeploymentImageRef.server"; import { DeleteRepositoryCommand } from "@aws-sdk/client-ecr"; @@ -12,6 +13,7 @@ describe.skipIf(process.env.RUN_REGISTRY_TESTS !== "1")("getDeploymentImageRef", process.env.DEPLOY_REGISTRY_HOST || "123456789012.dkr.ecr.us-east-1.amazonaws.com"; const testNamespace = process.env.DEPLOY_REGISTRY_NAMESPACE || "test-namespace"; const testProjectRef = "proj_test_" + Math.random().toString(36).substring(7); + const testProjectRef2 = testProjectRef + "_2"; const registryTags = process.env.DEPLOY_REGISTRY_ECR_TAGS || "test=test,test2=test2"; const roleArn = process.env.DEPLOY_REGISTRY_ECR_ASSUME_ROLE_ARN; @@ -30,13 +32,23 @@ describe.skipIf(process.env.RUN_REGISTRY_TESTS !== "1")("getDeploymentImageRef", try { const { region, accountId } = parseEcrRegistryDomain(testHost); const ecr = await createEcrClient({ region, assumeRole }); - await ecr.send( - new DeleteRepositoryCommand({ - repositoryName: `${testNamespace}/${testProjectRef}`, - registryId: accountId, - force: true, - }) - ); + + await Promise.all([ + ecr.send( + new DeleteRepositoryCommand({ + repositoryName: `${testNamespace}/${testProjectRef}`, + registryId: accountId, + force: true, + }) + ), + ecr.send( + new DeleteRepositoryCommand({ + repositoryName: `${testNamespace}/${testProjectRef2}`, + registryId: accountId, + force: true, + }) + ), + ]); } catch (error) { console.warn("Failed to delete test repository:", error); } @@ -60,20 +72,37 @@ describe.skipIf(process.env.RUN_REGISTRY_TESTS !== "1")("getDeploymentImageRef", }); it("should create ECR repository and return correct image ref", async () => { - const imageRef = await getDeploymentImageRef({ + const imageRef1 = await getDeploymentImageRef({ host: testHost, namespace: testNamespace, - projectRef: testProjectRef, + projectRef: testProjectRef2, nextVersion: "20250630.1", environmentSlug: "test", registryTags, assumeRole, }); - expect(imageRef.imageRef).toBe( - `${testHost}/${testNamespace}/${testProjectRef}:20250630.1.test` + expect(imageRef1.imageRef).toBe( + `${testHost}/${testNamespace}/${testProjectRef2}:20250630.1.test` ); - expect(imageRef.isEcr).toBe(true); + expect(imageRef1.isEcr).toBe(true); + expect(imageRef1.repoCreated).toBe(true); + + const imageRef2 = await getDeploymentImageRef({ + host: testHost, + namespace: testNamespace, + projectRef: testProjectRef2, + nextVersion: "20250630.2", + environmentSlug: "test", + registryTags, + assumeRole, + }); + + expect(imageRef2.imageRef).toBe( + `${testHost}/${testNamespace}/${testProjectRef2}:20250630.2.test` + ); + expect(imageRef2.isEcr).toBe(true); + expect(imageRef2.repoCreated).toBe(false); }); it("should reuse existing ECR repository", async () => {