From 1934450f3c67358b01dfff21e8f8a6e5d4ba1a99 Mon Sep 17 00:00:00 2001 From: ianedwards Date: Mon, 9 Oct 2023 17:42:00 -0400 Subject: [PATCH] POR-1902 validate name against existing porter apps (#3777) --- dashboard/src/lib/porter-apps/index.ts | 8 +++++- .../app-dashboard/create-app/CreateApp.tsx | 28 ++++++++++++++----- internal/repository/test/porter_app.go | 1 + 3 files changed, 29 insertions(+), 8 deletions(-) diff --git a/dashboard/src/lib/porter-apps/index.ts b/dashboard/src/lib/porter-apps/index.ts index 76280d7c2d..7ca7a7c8c8 100644 --- a/dashboard/src/lib/porter-apps/index.ts +++ b/dashboard/src/lib/porter-apps/index.ts @@ -59,7 +59,13 @@ export const deletionValidator = z.object({ export const clientAppValidator = z.object({ name: z.object({ readOnly: z.boolean(), - value: z.string(), + value: z + .string() + .min(1, { message: "Name must be at least 1 character" }) + .max(30, { message: "Name must be 30 characters or less" }) + .regex(/^[a-z0-9-]{1,61}$/, { + message: 'Lowercase letters, numbers, and "-" only.', + }), }), envGroups: z .object({ name: z.string(), version: z.bigint() }) diff --git a/dashboard/src/main/home/app-dashboard/create-app/CreateApp.tsx b/dashboard/src/main/home/app-dashboard/create-app/CreateApp.tsx index c202661219..df383fe8f2 100644 --- a/dashboard/src/main/home/app-dashboard/create-app/CreateApp.tsx +++ b/dashboard/src/main/home/app-dashboard/create-app/CreateApp.tsx @@ -80,7 +80,7 @@ const CreateApp: React.FC = ({ history }) => { const { maxCPU, maxRAM } = useClusterResourceLimits({ projectId: currentProject?.id, clusterId: currentCluster?.id, - }) + }); const { data: porterApps = [] } = useQuery( ["getPorterApps", currentProject?.id, currentCluster?.id], @@ -513,7 +513,7 @@ const CreateApp: React.FC = ({ history }) => { placeholder="ex: academic-sophon" type="text" width="300px" - error={errors.app?.name?.message} + error={errors.app?.name?.value?.message} disabled={name.readOnly} disabledTooltip={ "You may only edit this field in your porter.yaml." @@ -585,10 +585,23 @@ const CreateApp: React.FC = ({ history }) => { setValue("source.image", { ...image, repository: uri })} + setImageUri={(uri: string) => + setValue("source.image", { + ...image, + repository: uri, + }) + } imageTag={image?.tag ?? ""} - setImageTag={(tag: string) => setValue("source.image", { ...image, tag })} - resetImageInfo={() => setValue("source.image", { ...image, repository: "", tag: "" })} + setImageTag={(tag: string) => + setValue("source.image", { ...image, tag }) + } + resetImageInfo={() => + setValue("source.image", { + ...image, + repository: "", + tag: "", + }) + } /> ) ) : null} @@ -614,8 +627,9 @@ const CreateApp: React.FC = ({ history }) => { } > {detectedServices.count > 0 - ? `Detected ${detectedServices.count} service${detectedServices.count > 1 ? "s" : "" - } from porter.yaml.` + ? `Detected ${detectedServices.count} service${ + detectedServices.count > 1 ? "s" : "" + } from porter.yaml.` : `Could not detect any services from porter.yaml. Make sure it exists in the root of your repo.`} diff --git a/internal/repository/test/porter_app.go b/internal/repository/test/porter_app.go index cb9eef74da..bb51fc52f1 100644 --- a/internal/repository/test/porter_app.go +++ b/internal/repository/test/porter_app.go @@ -34,6 +34,7 @@ func (repo *PorterAppRepository) UpdatePorterApp(app *models.PorterApp) (*models return nil, errors.New("cannot write database") } +// ListPorterAppByClusterID is a test method that is not implemented func (repo *PorterAppRepository) ListPorterAppByClusterID(clusterID uint) ([]*models.PorterApp, error) { return nil, errors.New("cannot write database") }