07 October 2013

Visualizing User's Permissions Across Profiles and Permission Sets


Matt Lamb, a salesforce.com MVP at Appirio, responded to a question about whether it's worth just using profiles or if administrators should also use permission sets when assigning permissions to users. 

Matt tweeted, "The modularity [of permission sets] is awesome. In practice I've found they make auditing (e.g. "Who can Delete Accounts?") very difficult."

It's true that auditing can be difficult. I'd like to show you some simple steps that make the process much easier.

Permission sets were created to enable the layering of permissions. This allows administrators to meet use cases where profiles alone cannot go. Permission sets' modularity provides everything from the ability to layer a single permission to providing access to whole applications across different regions and lines of business.

Adopting permission sets introduces an auditing challenge. Now that permissions span a user's profile and all of their permission sets, it's challenging to determine why a user has access (e.g. "Who can delete accounts?").

I don't buy the argument that an administrator should rely solely on a profile because it's somehow more auditable than permission sets. I've even heard that 'CTRL-F' on a profile is a best practice when determining what a user has access to.

Some people may have seen me roll the Standard User profile out on over forty feet of paper in past Dreamforce sessions.

But what many admins may forget is that there's more than forty feet of permissions there. To view page layout assignments, record type settings, and field level security, you need to click into other pages. So even if you constrain yourself to only using profiles, they are still fundamentally not self-auditing.

Ultimately, what we all want is a visualization and reporting tool that allows us to audit what a user has been assigned. While we don't have a declarative reporting interface to display this information, we do have a robust API that allows a developer to build administrative tools to visualize and report on a user's permissions.

Last year, Doug Bitting created exactly that. His tool allows you to easily audit a user's permissions across both their profile and all of their permission sets in a highly visual manner.

As an example, Shawna Wolverton as a user in my org has one profile and many permission sets assigned to her.


When I click on the 'Display Perms' custom link on her user page, I can visualize the permissions assigned her.  I also start to get some sense of exactly how many permissions can be assigned a single user.



We can also report on the object and field permissions that the user has.


Finally, we can report on setup entity access permissions such as Apex Class and Apex Page access.


Doug made it very easy to download and configure my organization with this functionality.

I went to github (https://github.com/forcedotcom/user-access-visualization) and followed his directions in the Readme file. 

I first downloaded a ZIP of the repository. 

Then I used workbench to deploy a ZIP of the 'src' directory to my organization. (I could have used the force.com IDE to deploy the files as well; workbench is just my tool of choice.)

Last, I created a custom link on the user object. This link redirects an administrator to the visualforce page that will display the user's permissions. It knows who the user is because the page passes in the user id in the parameters of the URL (e.g. /apex/UserAccessDetails?uid={!User.Id}).


And there you have it. Using these methods, you can setup and audit a user's access across their profile and permission sets in around ten minutes.

39 comments:

  1. This is just what the doctor ordered. Well done. Can't wait to try it out. Any thoughts on how this could be leveraged to assess a full team's permissions?

    ReplyDelete
    Replies
    1. Thanks Muz!

      Tell me more about your use case. How do you define a 'full team' and what would you do with the information if you had it (since it could be millions of different permissions)?

      Also, check out the perm comparator (http://perm-comparator.herokuapp.com) which allows you to compare permissions between users, profiles, and permission sets. This may help you with your use case.

      Delete
  2. Running this in a developer edition with a packaging namespace threw a null pointer exception when retrieving the custom object information - changing the apiVersion of the UserAccessDetailsController.cls-meta.xml file to 29 (the repository has it at 25) fixed the problem for me.

    ReplyDelete
    Replies
    1. I did what you stated but I still get the null exception. Should I update all the XML's in the package to api version 29.

      Delete
    2. Just update the one file to the latest version.

      Delete
  3. I'm trying to audit users' access to records (accounts and opportunities) based on Territory, Role and Sharing Rule. Essentially, a matrix of "who sees what and why?". Can something like this deliver that kind of detail? Thanks!

    ReplyDelete
    Replies
    1. Hi Tyler - unfortunately not. This only visualizes the permissions that a user has assigned through their profile or permission sets. You would need to query the sharing tables for this information which is based on role, group, and territory rather than profile and permission set.

      Delete
  4. I must say I think I'm in love with Doug!

    Working on a multi-org/multi-country implementation and leveraging permission sets so we don't end up with 300+ profiles. It's been a huge challenge to see how the permission sets layer on top of each other and which ones can have items removed.

    This is BRILLIANT! In the first 5 minutes of using it I identified 2 security errors in our configuration!

    Thank you thank you thank you! I've shared this blog with my entire team and it will become a best practice for us for sure!

    ReplyDelete
    Replies
    1. Thanks VeevaEms!!! I shared your comment with Doug and he loved it. Hope this app works out for you.

      Delete
  5. This comment has been removed by the author.

    ReplyDelete
  6. very very cool. Now to dive into it an figure out how hard it would be to generalize this into a "Who Can Do What" app:

    https://sites.google.com/site/ezrakenigsberg/app-hitlist#WhoCanDoWhat

    ReplyDelete
    Replies
    1. Hey Ezra,

      I dig it! Also check out github.com/atorman/customSharingButton for a variation of determining access at a record level.

      Delete
  7. I am getting the following error when trying to deploy with workbench - No package.xml found. Any ideas?

    ReplyDelete
    Replies
    1. I have got the same problem. Any advise appreciated.

      Matthias

      Delete
    2. Two troubleshooting tips:
      1. on the deploy screen, make sure you check, 'Allow Missing Files'
      2. make sure when you zip, package.xml is in the top level
      3. when you zip (which you should do after uncompressing it), try using the command line (especially if you're like me and are on MacOSX):

      cd /Users/adamtorman/Downloads/user-access-visualization-master/UserAccessVisualization/src
      zip -r UserAccessVisualization.zip src

      Delete
    3. Thanks for your feedback.

      I was a little bit to fast and used the downloaded zip file for the deployment, instead of creating a new one from the src directory. After that I managed to install the package, but with one error message:

      It states the fileName: src/staticresources/css.resource is already in use. Choose another one. Do I manually need to incorporate the css content in the existing file?

      Regards,

      Matthias

      Delete
    4. Hi Matthias,

      You can manually incorporate the css content or just rename the css in the src directory to css1.resource and css1.resource-meta.xml and modify the visual force page to incorporate the newly named css resource ( ) just to keep the resources different.

      Delete
  8. Hi Adam,

    I've successfully deployed the src.zip in our Sandbox but it fails in our production org. Any suggestions on where to start looking?

    thanks
    Bruce

    ReplyDelete
    Replies
    1. Hi Bruce,

      Are you getting an error when you deploy? Do you have any managed packages that are in your production that aren't in your sandbox? Did all the apex tests run during deployment? Did you try migrating the components using a change set from sandbox or did you just deploy directly using Force.com IDE or workbench? Thanks!

      Delete
  9. Hi Adam,

    is there any way to make your visualisation language independend? The main UI language in our org is German. The "Object Information" then is not displayed properly - no colors for the actions create, read, edit, delete etc. are visible. When the language is switched to English everything works fine.

    Thanks,

    Matthias

    ReplyDelete
    Replies
    1. Hi Matthias - this visualization tool was designed to be open sourced. The code can be found at https://github.com/forcedotcom/user-access-visualization. The developer who originally worked on it, Doug Bitting, is open to all and any pull requests. Thanks!

      Adam

      Delete
  10. Hi Adam,

    Quick question, I am finding that not all permissions are included, which I believe is a data model issue but I am hoping for some confirmation. Specifically, I am unable to, in this application and SOQL, query for Manage Public List Views. Any insight on this?

    ReplyDelete
    Replies
    1. Hi Tyler - I'm guessing this is the same question as the following twitter conversation (https://twitter.com/techbusinessman/status/430420739213119488) in which case you already know that we added many of the missing user permissions to the API in Spring '14 release.

      Delete
  11. I'm getting
    Maximum view state size limit (135KB) exceeded. Actual view state size for this page was 240.562KB

    ReplyDelete
    Replies
    1. Need some more information about this error. thanks!

      Delete
    2. I too am having the same issue with the view state size limit. Does anyone have a solution?

      Delete
  12. Just came across this and it will definitly help with reviewing and setting up permissions. I do have a question on test coverage. There doesn't seem to be any with this, so will negativly affect a prod environment?

    Thanks
    Chris.

    ReplyDelete
    Replies
    1. Hi Chris,

      This comment is probably better on Doug's actual github posting. I think he intentionally didn't write tests to demonstrate functionality only assuming that any developer would take it an create something specific to their production environment. I'm sorry there aren't any tests to support deployment.

      Delete
  13. Does anybody know how to increase test coverage for this. I am getting 71% and need to get up to 75% for the deployment to work

    ReplyDelete
  14. hey,

    I am running into an issue that i hope someone may have a lead on. I was able to deploy the src with no issues and i have it in a sandbox environment at the moment. When i run the VF page i get:

    "Apex CPU time limit exceeded
    An unexpected error has occurred. Your solution provider has been notified. (Database)"

    I was able to get the page to work once, but i cant replicate that even with the same user again. I tried up-ing all the files to API 29 just to make sure it was not something with 25 causing the issue.

    i hope it is something easy to adjust. if anyone has a suggestion i am open to it. This app looks great but right now it just bombs out on me.

    Thank you!

    ReplyDelete
  15. Hi, i recognize how valuable this tool is. Thank you for sharing this!

    I was able to deploy the src zip to production. I am hoping that someone can help me resolve a null pointer error. "Attempt to de-reference a null object" I receive this error when I pass a valid user id to the visualforce page like so .../apex/UserAccessDetails?uid=00560000004HKou. I've updated the Class versions in an attempt to fix this problem but doing so did not solve the issue.

    Here's the track trace from my debug log:

    11:02:49.444 (1444075329)|FATAL_ERROR|System.NullPointerException: Attempt to de-reference a null object
    Class.UserAccessDetailsController.getObjectLabels: line 289, column 1

    11:02:49.444 (1444089422)|CODE_UNIT_FINISHED|UserAccessDetailsController invoke(getobjectLabels)
    11:02:49.444 (1444158245)|CODE_UNIT_FINISHED|UserAccessDetailsController get(objectLabels)

    Here's the snippet of code from the "UserAccessDetails" class. Based on the debug log it seems to be throwing the null pointer exception on line 289. The query on line 287 and 288 works in my Org -- that is it selects data just fine. Does anything look wrong with line 289?

    Thanks for the information


    //287
    for (ObjectPermissions op : [SELECT SObjectType FROM ObjectPermissions

    //288
    WHERE Parent.Profile.Name = 'System Administrator']) {
    //289
    result.add(new NameLabel(op.SObjectType,
    //290
    describe.get(op.SObjectType).getDescribe().getLabel()));

    ReplyDelete
  16. For those reading my last post, I made a typo in my last post. The code snippet that I provided is actually from the "UserAccessDetailsController" class. Thanks in advance!

    ReplyDelete
  17. After looking deeper into the debug logs I realized that op.SObjectType eventually returned a null value during the looping. After controlling for this (by excluding null values) I retried. Next I hit a 50001 row limit error. To get past this I added a LIMIT clause to this query in the UserAccessDetailsController class "SELECT ParentId, SetupEntityIdFROM SetupEntityAccessWHERE SetupEntityType = :seaType LIMIT 100". 100 was an arbitrary number. I'm still looking into why i received the 50001 row limit during the execution of the limitless query. Next, the visualforce page loaded for certain users.For some users it failed with the reason "Maximum view state size limit (135KB) exceeded. Actual view state size for this page was 141.109KB"

    ReplyDelete
    Replies
    1. Hi Could you tell me how did you debug the "Attempt to de-reference a null object"
      I am running into same error
      How did you control this by excluding null values?

      Delete
  18. FWIW I only recently realized i can use enhanced list views on permissions sets in much the same was as on profiles to see which perm sets give CRED access on an object.

    Its a bit tricky to get the filters right, but w/ a bit of trial and error you can get it to work.

    I cant get this to display record type access and i'm sure other things as well, but its a good way to audit CRED access by Perm Set.

    ReplyDelete
  19. This comment has been removed by the author.

    ReplyDelete
    Replies
    1. This comment has been removed by the author.

      Delete
  20. I got this working by updating the API to 36.0 however I get double entries on the object labels.

    ReplyDelete
    Replies
    1. Just noticed this is for OOTB objects like Account, Contact, Opportunity

      Delete