{"record":{"id":"a78b28c4e03c0b70","repo":"SonarSource/sonarqube","slug":"insufficient-privileges-a78b28","errorCode":null,"errorMessage":"Insufficient privileges","messagePattern":"Insufficient privileges","errorType":"exception","errorClass":"ForbiddenException","httpStatus":403,"severity":"error","filePath":"server/sonar-webserver-webapi/src/main/java/org/sonar/server/qualityprofile/ws/QProfileWsSupport.java","lineNumber":113,"sourceCode":"      return true;\n    }\n    UserDto user = dbClient.userDao().selectByLogin(dbSession, userSession.getLogin());\n    checkState(user != null, \"User from session does not exist\");\n    return dbClient.qProfileEditUsersDao().exists(dbSession, profile, user)\n      || dbClient.qProfileEditGroupsDao().exists(dbSession, profile, userSession.getGroups());\n  }\n\n  boolean canAdministrate(QProfileDto profile) {\n    if (profile.isBuiltIn() || !userSession.isLoggedIn()) {\n      return false;\n    }\n    return userSession.hasPermission(GlobalPermission.ADMINISTER_QUALITY_PROFILES);\n  }\n\n  public void checkCanEdit(DbSession dbSession, QProfileDto profile) {\n    checkNotBuiltIn(profile);\n    if (!canEdit(dbSession, profile)) {\n      throw insufficientPrivilegesException();\n    }\n  }\n\n  public void checkCanAdministrate(QProfileDto profile) {\n    checkNotBuiltIn(profile);\n    if (!canAdministrate(profile)) {\n      throw insufficientPrivilegesException();\n    }\n  }\n\n  void checkNotBuiltIn(QProfileDto profile) {\n    checkRequest(!profile.isBuiltIn(), \"Operation forbidden for built-in Quality Profile '%s' with language '%s'\", profile.getName(), profile.getLanguage());\n  }\n}\n","sourceCodeStart":95,"sourceCodeEnd":128,"githubUrl":"https://github.com/SonarSource/sonarqube/blob/184c821202192afc1c599fc912d0889b69fffa53/server/sonar-webserver-webapi/src/main/java/org/sonar/server/qualityprofile/ws/QProfileWsSupport.java#L95-L128","documentation":"QProfileWsSupport.checkCanEdit guards all quality-profile editing web services (adding/deleting rules, activating rules, changing inheritance). Editing requires the global ADMINISTER_QUALITY_PROFILES permission or a per-profile editing grant for the user or one of their groups; the user must also pass canEdit in QProfileWsSupport. Built-in profiles are rejected before the permission check via checkNotBuiltIn.","triggerScenarios":"Calling api/qualityprofiles/activate_rule, change_parent, deactivate_rule, rename, or delete on a profile the user cannot edit — no global 'Administer Quality Profiles' permission and no user/group edit permission on that profile.","commonSituations":"Teams copying SonarSource's per-profile permission model but forgetting to grant group edit rights; users editing a built-in profile like 'Sonar way' (fails checkNotBuiltIn first, but permission also missing); post-upgrade permission resets.","solutions":["Grant global 'Administer Quality Profiles' permission to the user.","Or grant per-profile user/group edit permission via api/qualityprofiles/add_user / add_group (permissions endpoints).","If the target is a built-in profile, copy it first (api/qualityprofiles/copy) and edit the copy.","Check group membership — per-profile grants are often made to a group the user must belong to."],"exampleFix":"// before: user edits profile without rights\ncurl -u usertoken: -X POST \"$SONAR/api/qualityprofiles/activate_rule?language=java&qualityProfile=TeamProfile&rule=squid:S001\"\n\n// after: grant edit permission on the profile\ncurl -u admintoken: -X POST \"$SONAR/api/qualityprofiles/add_group?language=java&qualityProfile=TeamProfile&groupName=devs\"","handlingStrategy":"validation","validationCode":"// Built-in profiles are never editable:\nif (profile.isBuiltIn()) return false;\n// Require global permission:\ncurl -u \"$TOKEN\": \"$SONAR/api/permissions/user?login=$USER\" | grep 'profileadmin'","typeGuard":"boolean canEditProfile(QProfileDto p, UserSession s) {\n  return !p.isBuiltIn() && s.hasPermission(GlobalPermission.ADMINISTER_QUALITY_PROFILES);\n}","tryCatchPattern":null,"preventionTips":["Copy built-in profiles before customizing; never try to edit them.","Grant per-profile edit to a group and keep the right users in it.","Separate edit vs administration endpoints in automation scripts.","Re-audit quality-profile permissions after server upgrades."],"tags":["sonarqube","webapi","authorization","quality-profiles"],"backgroundTag":"insufficient-permissions","analyzedSha":"184c821202192afc1c599fc912d0889b69fffa53","analyzedAt":"2026-09-09T12:23:51.573Z","contentChangedAt":"2026-09-09T12:23:51.573Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}