medusajs/medusa · error · MedusaError

Policy with id "${req.params.id}" not found

Error message

Policy with id "${req.params.id}" not found

What it means

Thrown by POST /admin/rbac/policies/:id when the pre-update existence check (fields: ["id"]) returns no policy. Like other update routes, it verifies the policy exists before running updateRbacPoliciesWorkflow.

Source

Thrown at packages/medusa/src/api/admin/rbac/policies/[id]/route.ts:63

/**
 * @ignore
 * @featureFlag rbac
 */
export const POST = async (
  req: AuthenticatedMedusaRequest<AdminUpdateRbacPolicyType>,
  res: MedusaResponse
) => {
  const query = req.scope.resolve(ContainerRegistrationKeys.QUERY)
  const { data: existing } = await query.graph({
    entity: "rbac_policy",
    filters: { id: req.params.id },
    fields: ["id"],
  })

  const existingPolicy = existing[0]
  if (!existingPolicy) {
    throw new MedusaError(
      MedusaError.Types.NOT_FOUND,
      `Policy with id "${req.params.id}" not found`
    )
  }

  const { result } = await updateRbacPoliciesWorkflow(req.scope).run({
    input: {
      selector: { id: req.params.id },
      update: req.validatedBody,
    },
  })

  const { data: policies } = await query.graph({
    entity: "rbac_policy",
    filters: { id: result[0].id },
    fields: req.queryConfig.fields,
  })

View on GitHub (pinned to 5e06e544a2)

Solutions

  1. Re-fetch policies and merge your change onto the current version before updating
  2. On 404, recreate the policy instead of updating
  3. Refresh RBAC state after bulk policy imports/regenerations

Example fix

// before
await sdk.client.fetch(`/admin/rbac/policies/${id}`, { method: "POST", body: updatedPolicy })

// after
try {
  await sdk.client.fetch(`/admin/rbac/policies/${id}`, { method: "POST", body: updatedPolicy })
} catch (e) {
  if (e.statusCode === 404) { await sdk.client.fetch("/admin/rbac/policies", { method: "POST", body: updatedPolicy }); return }
  throw e
}
Defensive patterns

Strategy: try-catch

Validate before calling

const { policies } = await sdk.client.fetch("/admin/rbac/policies", { query: { id: [policyId] } })
if (policies.length === 0) throw new Error(`Policy ${policyId} gone; recreate instead of update`)

Try / catch

try {
  await updatePolicy(id, patch)
} catch (e: any) {
  if (e.statusCode === 404) { await createPolicy(patch); return }
  throw e
}

Prevention

When it happens

Trigger: Updating a policy id that does not exist or was concurrently deleted via POST /admin/rbac/policies/:id with an update body.

Common situations: Two admins editing RBAC policies simultaneously, policy regeneration between load and save, or stale ids in permission-sync scripts.

Understand the failure class

Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.

Related errors


AI-assisted analysis of medusajs/medusa@5e06e544a2 (2026-08-27). Data as JSON: /api/errors/ce1cdcece3bfaced. Report an issue: GitHub.