3

Shiro provides cache feature but in my case, I'm using dynamic roles and permissions for the users. I need to expire the cache for a particular user if any so that changes in permissions immediately affect to user.

There is a method in Realm, but how I get an instance of associated realm to invoke method to clear cache.

Jens Piegsa
  • 7,399
  • 5
  • 58
  • 106
Ankit Katiyar
  • 2,631
  • 2
  • 20
  • 30

2 Answers2

6

I ended up exposing the private method "clearCachedAuthorizationInfo" in the extended Realm of AuthorizingRealm. Then just pass in the principals.

public class MyRealm extends AuthorizingRealm {
    //...
    @Override
    public void clearCachedAuthorizationInfo(PrincipalCollection principals)
    {
        super.clearCachedAuthorizationInfo(principals);
    }
    //...
}

to clear the authorization cache:

realm.clearCachedAuthorizationInfo( SecurityUtils.getSubject().getPrincipals() );

I think this is a bit cleaner/safer because this method has additional checks against null on the cache and will ensure you get a reference to the cache if one exists. Simply calling getAuthorizationCache() doesn't do this and may or may not work all the time.

You do need to maintain a reference to the realm. I did this by initializing Shiro via Spring and then injecting it as a Singleton bean wherever I needed it.

schnatterer
  • 7,525
  • 7
  • 61
  • 80
Jeff
  • 3,549
  • 1
  • 14
  • 11
  • Hey Thanks for response. But I am not using spring so i have to configure shiro using INI they how I will get the realm instance used by shiro. I tried to configure shiro through java code, but java-code configuration doesn't work it says no realm configured. – Ankit Katiyar Apr 21 '14 at 06:12
  • 1
    To fetch all the realms available you can use: Collection realms = ((RealmSecurityManager)SecurityUtils.getSecurityManager()).getRealms(); You can then see which realms have the method that exposed clearing the Authorization Info and call it on those realms. – Stephen M -on strike- Aug 05 '14 at 21:59
1

If you check out the source of the method getAuthorizationInfo in AuthorizingRealm, you see it is simply using a key/value store to cache the authorization info.

It uses the PrincipalCollection object as a key.

So if you call something like:

realm.getAuthorizationCache().remove(SecurityUtils.getSubject().getPrincipals())

the cache should normally be cleared.

Wouter
  • 3,976
  • 2
  • 31
  • 50