diff --git a/app/pages/project/floating-ips/AttachFloatingIpModal.tsx b/app/pages/project/floating-ips/AttachFloatingIpModal.tsx index 43ce1c0901..b8cc1fb925 100644 --- a/app/pages/project/floating-ips/AttachFloatingIpModal.tsx +++ b/app/pages/project/floating-ips/AttachFloatingIpModal.tsx @@ -36,12 +36,10 @@ function FloatingIpLabel({ fip }: { fip: FloatingIp }) { export const AttachFloatingIpModal = ({ floatingIps, instance, - project, onDismiss, }: { floatingIps: Array instance: Instance - project: string onDismiss: () => void }) => { const queryClient = useApiQueryClient() @@ -88,8 +86,7 @@ export const AttachFloatingIpModal = ({ disabled={!floatingIp} onAction={() => floatingIpAttach.mutate({ - path: { floatingIp }, - query: { project }, + path: { floatingIp }, // note that this is an ID! body: { kind: 'instance', parent: instance.id }, }) } diff --git a/app/pages/project/instances/instance/tabs/NetworkingTab.tsx b/app/pages/project/instances/instance/tabs/NetworkingTab.tsx index 309f68b317..1315fcd6f7 100644 --- a/app/pages/project/instances/instance/tabs/NetworkingTab.tsx +++ b/app/pages/project/instances/instance/tabs/NetworkingTab.tsx @@ -335,7 +335,6 @@ export function NetworkingTab() { floatingIps={availableIps} instance={instance} onDismiss={() => setAttachModalOpen(false)} - project={project} /> )} diff --git a/mock-api/msw/db.ts b/mock-api/msw/db.ts index e54ad02450..fb75391799 100644 --- a/mock-api/msw/db.ts +++ b/mock-api/msw/db.ts @@ -14,6 +14,7 @@ import * as mock from '@oxide/api-mocks' import { json } from '~/api/__generated__/msw-handlers' import { pick } from '~/util/object' +import { commaSeries } from '~/util/str' import type { Json } from '../json-type' import { internalError } from './util' @@ -25,6 +26,11 @@ export const notFoundErr = (msg?: string) => { return json({ error_code: 'ObjectNotFound', message } as const, { status: 404 }) } +export const badSelectorErr = (resource: string, parents: string[]) => { + const message = `when ${resource} is specified by ID, ${commaSeries(parents, 'and')} should not be specified` + return json({ error_code: 'InvalidRequest', message }, { status: 400 }) +} + export const lookupById = (table: T[], id: string) => { const item = table.find((i) => i.id === id) if (!item) throw notFoundErr @@ -85,7 +91,10 @@ export const lookup = { floatingIp({ floatingIp: id, ...projectSelector }: PP.FloatingIp): Json { if (!id) throw notFoundErr - if (isUuid(id)) return lookupById(db.floatingIps, id) + if (isUuid(id)) { + if (projectSelector.project) throw badSelectorErr('floating IP', ['project']) + return lookupById(db.floatingIps, id) + } const project = lookup.project(projectSelector) const floatingIp = db.floatingIps.find(