Writing a plugin to have extra permissions

Steven Cogorno June 16, 2011

Is it possible to create a plugin using the SDK that will allow a user to run an action that he or she wouldn't ordinarily have permission to do?

Here's a specific example:

A number of users in our company need to make new user accounts for outside contacts. We want them to follow a specific process to do this (we're writing a plugin to manage the process). The users don't have permission to create users, but we would like the plugin to be able to add the user on their behalf.

We definitely do *not* want to give these users arbitrary account creation privileges, hence the plugin. However, Confluence is cross-checking the API calls with the user's permission. Is there to add something to the plugin that will allow the user add operation?

Thanks!

-Steve

3 answers

1 accepted

Comments for this post are closed

Community moderators have prevented the ability to post new answers.

Post a new question

4 votes
Answer accepted
CharlesA
Rising Star
Rising Star
Rising Stars are recognized for providing high-quality answers to other users. Rising Stars receive a certificate of achievement and are on the path to becoming Community Leaders.
June 26, 2011

Very few API calls in Confluence are checked for permissions, it's assumed that the permission checks are done in the higher-level code that accesses the base API. That said, there are some APIs related to modifying users and changing permissions that do check permissions for weird historical reasons. (Largely to prevent the system from getting into states where, for example, nobody has admin access)

One thing you can do is temporarily set the current user to some other identity:

User currentUser = AuthenticatedUserThreadLocal.getUser();
try {
    AuthenticatedUserThreadLocal.setUser(someAdminUser);
    doStuffHere();
} finally {
    AuthenticatedUserThreadLocal.setUser(currentUser);
}

This code isn't very friendly to general-purpose plugins as it needs some way to acquire a valid admin user to run as. Also there's a slight chance that it might not work with some ancient, ancient code that predates the use of AuthenticatedUserThreadLocal. That said, it'll work in a pinch.

Steven Cogorno June 27, 2011

Thanks Charles!

I'll give this a try. :-)

-Steve

0 votes
Olivier Barthelemy November 16, 2016

Sorry to up this, but my question is related enough to keep it in the same place.

I was trying to get users for a given role of a given project in the code of a plugin. I first used ProjectRoleService.getProjectRoleActors(). This failed, and the Error Collection object said that it was a permisson issue of the current user. Which made me wonder how some other plugins do the same thing with the same JIRA user. Then i tried ProjectRoleManager.getProjectRoleActors(), not expecting a different result, but this one worked.

OK, good for me, but this raises a security question

So does this means that JIRA plugins can do anything, as long as you call the code to do it, regardless of the permission of the current user? That there is the assumption that if a plugin was added by the JIRA admin, then it means the admin 'accepted' that regular users will be able to do anything the plugin includes so regular users can gain rights to what they can not normally do?

In that case, shouldn't there be a 'permission system', like on Android, that allows an admin to see what a plugin will be able to do regardless of user permissions? For example a modification of the API, where developpers would be forced to 'declare' various permissions requirements somewhere within the plugin metadata, which permissions should then be requested in plugin code for operations that currently do not check anything, and from where a list of permissions could be asked to the JIRA admin at install?

0 votes
Rex Kidwell May 27, 2015

I have actually implemented this in our custom authenticator in Conf 5.1.5. Our desire was to add a user if they didn't already exist in the cwd_user table when they navigate to Confluence. I ended up using:

try {
    AuthenticatedUserThreadLocal.setUser(someAdminUser, someAdminUserName, someAdminUserEmail);
    doStuffHere();
    createUser(...);
    addMembership(...);
 } finally {
    AuthenticatedUserThreadLocal.reset;
}

Basically, the current user hasn't been authenticated yet, so its anonymous, and no need to restore to a nonexistent user. btw - just using "someAdminUser" didn't work for me; runtime exceptions. And just for clarity for all, the AuthenticatedUserThreadLocal is required to be able to add a group membership, like the default group every user has to be in - confluence-users.

TAGS
AUG Leaders

Atlassian Community Events