{"record":{"id":"0bdb58f57eab9bf3","repo":"hashicorp/vault","slug":"could-not-update-allowed-roles-for-selected-databa","errorCode":null,"errorMessage":"Could not update allowed roles for selected database: ${e.errors.join(', ')}","messagePattern":"Could not update allowed roles for selected database: (.+?)","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"ui/app/adapters/database/role.js","lineNumber":222,"sourceCode":"      data = {\n        ...serializedData,\n        username: snapshot.attr('username'), // username is required for updating a static role\n      };\n    } else {\n      data = serializedData;\n    }\n\n    return this.ajax(this.urlFor(backend, id, roleType), 'POST', { data }).then(() => data);\n  },\n\n  checkError(e) {\n    if (e.httpStatus === 403) {\n      // The user does not have the permission to update the connection. This\n      // can happen if their permissions are limited to the role. In that case\n      // we ignore the error and continue updating the role.\n      return;\n    }\n    throw new Error(`Could not update allowed roles for selected database: ${e.errors.join(', ')}`);\n  },\n});\n","sourceCodeStart":204,"sourceCodeEnd":225,"githubUrl":"https://github.com/hashicorp/vault/blob/744b611b5700b3b7f82d76b4d6938a91b9989367/ui/app/adapters/database/role.js#L204-L225","documentation":"Thrown by the Vault UI's Ember Data adapter for database secrets engine roles (ui/app/adapters/database/role.js:222). Before creating or deleting a role, the adapter calls _updateAllowedRoles(), which loads the parent database connection record, adds/removes the role name from its allowed_roles list, and saves the connection. If that preliminary connection save fails with any HTTP status other than 403, checkError() rethrows with the joined error strings. A 403 is deliberately swallowed because a user whose policy only covers roles (not the connection) must still be able to save the role itself.","triggerScenarios":"Creating (createRecord) or deleting (deleteRecord) a dynamic or static role when the intermediate connection.save() (PUT/POST /v1/<mount>/config/<connection>) fails non-403: connection was deleted or renamed out-of-band (404), the database plugin rejects the payload (400), the external database is unreachable (500), or a network/adapter error where e.errors may even be undefined.","commonSituations":"Connection record removed in another tab or by another admin while the role form is open; the DB plugin cannot reach the external database so config writes fail; a policy that denies with 404 instead of 403; partially-granted ACLs that produce 400s on the connection update.","solutions":["Open the browser network tab (or inspect e.errors) to see the underlying status and message from the failed /v1/<mount>/config/<connection> request","Verify the connection still exists and its plugin is healthy: vault read <mount>/config/<connection>","Fix the external database connectivity or plugin error reported in e.errors, then retry the role save","If the user intentionally has role-only permissions, make sure their policy produces a 403 on the connection path so the UI correctly skips the allowed_roles update"],"exampleFix":"// before: role.save() fails with generic wrapped error\ntry {\n  await role.save();\n} catch (e) {\n  // 'Could not update allowed roles for selected database: ...'\n}\n\n// after: distinguish the connection-update failure from the role save\ntry {\n  await role.save();\n} catch (e) {\n  if (e.message.startsWith('Could not update allowed roles')) {\n    const detail = e.message.split(': ')[1];\n    this.flash.danger(`Connection update failed (${detail}). Verify the connection exists and the plugin is healthy.`);\n  } else {\n    throw e;\n  }\n}","handlingStrategy":"try-catch","validationCode":"// Before saving a new/deleted role, confirm the connection is readable and savable\nconst connection = await this.store.queryRecord('database/connection', { backend, id: db });\nif (!connection) {\n  throw new Error(`Connection ${db} not found on ${backend}; fix it before managing roles.`);\n}","typeGuard":null,"tryCatchPattern":"try {\n  await role.save();\n} catch (e) {\n  if (e.message.startsWith('Could not update allowed roles')) {\n    // 403 on the connection update is intentionally ignored inside the adapter;\n    // anything else means the allowed_roles sync genuinely failed — surface the detail\n    const detail = e.message.split(': ')[1] ?? 'unknown';\n    notifyUser(`Database connection update failed: ${detail}`);\n  } else {\n    throw e;\n  }\n}","preventionTips":["Keep the connection record (config) healthy before managing roles: verify vault read <mount>/config/<connection> succeeds","Grant role-managers either full connection update rights or a clean 403 deny — ambiguous non-403 failures abort the whole role save","Avoid deleting or renaming connections while other users have the roles tab open"],"tags":["database-secrets","ember-data","adapter","allowed-roles","http"],"backgroundTag":null,"analyzedSha":"744b611b5700b3b7f82d76b4d6938a91b9989367","analyzedAt":"2026-08-15T14:40:29.333Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}