You are viewing a plain text version of this content. The canonical link for it is here.
Posted to user@shiro.apache.org by Wolfgang Winter <w....@logitags.com> on 2012/11/15 18:26:33 UTC

Shiro Integration in Cibet framework

Hi,

for the next release of Cibet control framework (www.logitags.com/cibet) we
add integration with Shiro. Cibet allows amongst others dual control
mechanisms like Four-Eyes or Two-Man-Rule. The last one imposes that two
users are authenticated and authorized at the same time. That means while
the first user is logged in a second user must login and his permissions
checked. The Subject of the second user must not overwrite the Subject of
the first user in the session. Shiro allows this by implementing a
SessionStorageEvaluator which decides on a per-Subject basis if to store in
the session or not.

However, while this approach is perfect for application developers, it is
not when developing a framework like Cibet. The problem is that for
configuring an own SessionStorageEvaluator implementation I must make
assumptions about the configuration of the embedding application. This is
because configuration is possible only over the implementations, not the
Shiro interfaces:

A programmatic configuration equivalent to
  securityManager.subjectDAO.sessionStorageEvaluator =
$sessionStorageEvaluator 
implies that 
- DefaultSecurityManager is used
- DefaultSubjectDAO is used

because methods getSubjectDAO() and setSessionStorageEvaluator() are not
exposed in the interfaces but only in the implementations. Furthermore I
have to mark the Subject of the second user somehow to let my
SessionStorageEvaluator implementation decide to not store this one in the
session. However, Subject class and even DefaultSubject have no suitable
methods to mark and even then I fear I have to make assumptions about which
implementation is used.

My actual solution is to subclass the DefaultSecurityManager and overwrite
save(Subject subject) with an empty method. I use this CibetSecurityManager
for the second login like this:

   public void logonSecondUser(AuthenticationToken auth) {
      DefaultSecurityManager utilsSecMan = (DefaultSecurityManager)
SecurityUtils
            .getSecurityManager();

      SecurityManager secMan = new
CibetSecurityManager(utilsSecMan.getRealms());
      Subject subject = new Subject.Builder(secMan).sessionCreationEnabled(
            false).buildSubject();
      subject.login(auth);
      ...
      
This solution seems slightly better because the only assumption here is that
DefaultSecurityManager is used. However, if someone configures a custom
SecurityManager he will get a ClassCastException.

Why are the setter methods that are implicitly used in the ini configuration
not exposed in the interfaces but only in the implementations? For an
application developer this is okay, because he knows what he configures but
as a framework developer I want only deal with interfaces.

Or does anyone has a better solution for this issue?




--
View this message in context: http://shiro-user.582556.n2.nabble.com/Shiro-Integration-in-Cibet-framework-tp7577945.html
Sent from the Shiro User mailing list archive at Nabble.com.

Re: Shiro Integration in Cibet framework

Posted by Les Hazlewood <lh...@apache.org>.
Hi Wolfgang,

Could you please elaborate your particular use case and the expected
behavior?  Also, how it may or may not apply to requests and/or threads?

If we understand this better, we can suggest an implementation technique
that might be ideal for your requirements.

As to your comments about interfaces vs implementations, Shiro's interfaces
represent only what _must_ be supported for any given implementation, not
what could be supported.  This provides us (and Shiro users) the most
flexibility possible and is what allows Shiro to be so adaptable to any
runtime environment.  Configuration necessarily reflects
implementation-specific concepts, so you can configure objects (or nested
objects) based on your knowledge of the implementation (i.e. not all
implementations *should* support a setFoo(...) method, so it is
purposefully not defined in the interface).

That your current SecurityManager implementation is different than Shiro's
default implementation is not a bad thing at all - we try _very_ hard to
ensure that components only interact with interfaces where possible so we
_don't_ have tight coupling to implementations.  You should be able to swap
out almost any part of Shiro's SecurityManager object graph without
problems.

To corroborate this, there are only 2 locations in the entire Shiro
codebase (that are not test cases) that explicitly reference the
DefaultSecurityManager implementation:

The IniSecurityManagerFactory.createDefaultInstance()  (which can be
overridden for custom implementations if desired).
and
the Guice integration module's ShiroModule.bindSecurityManager (which can
also be easily overridden).

You can also redefine the SecurityManager implementation in the ini
config's [main] section easily without overriding anything:

securityManager = com.foo.my.SecurityManager

it's just that most people don't need to do this.

So, Shiro was designed explicitly to support your current behavior.
 However, if you don't want to override the DefaultSecurityManager
implementation, please elaborate your use case (multi Subject stuff) and we
can see if there is an easier way to solve that problem.

Best regards,

--
Les Hazlewood | @lhazlewood
CTO, Stormpath | http://stormpath.com | @goStormpath | 888.391.5282
Stormpath wins GigaOM Structure Launchpad Award! http://bit.ly/MvZkMk

On Thu, Nov 15, 2012 at 9:26 AM, Wolfgang Winter <w....@logitags.com>wrote:

> Hi,
>
> for the next release of Cibet control framework (www.logitags.com/cibet)
> we
> add integration with Shiro. Cibet allows amongst others dual control
> mechanisms like Four-Eyes or Two-Man-Rule. The last one imposes that two
> users are authenticated and authorized at the same time. That means while
> the first user is logged in a second user must login and his permissions
> checked. The Subject of the second user must not overwrite the Subject of
> the first user in the session. Shiro allows this by implementing a
> SessionStorageEvaluator which decides on a per-Subject basis if to store in
> the session or not.
>
> However, while this approach is perfect for application developers, it is
> not when developing a framework like Cibet. The problem is that for
> configuring an own SessionStorageEvaluator implementation I must make
> assumptions about the configuration of the embedding application. This is
> because configuration is possible only over the implementations, not the
> Shiro interfaces:
>
> A programmatic configuration equivalent to
>   securityManager.subjectDAO.sessionStorageEvaluator =
> $sessionStorageEvaluator
> implies that
> - DefaultSecurityManager is used
> - DefaultSubjectDAO is used
>
> because methods getSubjectDAO() and setSessionStorageEvaluator() are not
> exposed in the interfaces but only in the implementations. Furthermore I
> have to mark the Subject of the second user somehow to let my
> SessionStorageEvaluator implementation decide to not store this one in the
> session. However, Subject class and even DefaultSubject have no suitable
> methods to mark and even then I fear I have to make assumptions about which
> implementation is used.
>
> My actual solution is to subclass the DefaultSecurityManager and overwrite
> save(Subject subject) with an empty method. I use this CibetSecurityManager
> for the second login like this:
>
>    public void logonSecondUser(AuthenticationToken auth) {
>       DefaultSecurityManager utilsSecMan = (DefaultSecurityManager)
> SecurityUtils
>             .getSecurityManager();
>
>       SecurityManager secMan = new
> CibetSecurityManager(utilsSecMan.getRealms());
>       Subject subject = new Subject.Builder(secMan).sessionCreationEnabled(
>             false).buildSubject();
>       subject.login(auth);
>       ...
>
> This solution seems slightly better because the only assumption here is
> that
> DefaultSecurityManager is used. However, if someone configures a custom
> SecurityManager he will get a ClassCastException.
>
> Why are the setter methods that are implicitly used in the ini
> configuration
> not exposed in the interfaces but only in the implementations? For an
> application developer this is okay, because he knows what he configures but
> as a framework developer I want only deal with interfaces.
>
> Or does anyone has a better solution for this issue?
>
>
>
>
> --
> View this message in context:
> http://shiro-user.582556.n2.nabble.com/Shiro-Integration-in-Cibet-framework-tp7577945.html
> Sent from the Shiro User mailing list archive at Nabble.com.
>

Re: Shiro Integration in Cibet framework

Posted by Wolfgang Winter <w....@logitags.com>.
Thanks Les,
for your explanation about implementations and interfaces. I see your point
of view that you don’t want to force a custom implementation developer to
adapt all internal concepts of Shiro. That makes the interfaces clean and
easy to understand and use. The login method does essentially two major
things: authenticate the user and store somehow his Subject for later use.
For my use case I need only the first.

Cibet is kind of Aspect framework but more implementation driven than
AspectJ and alike. It allows by fine-grained configuration to control what
we call an event, which could be a method invocation, an EJB call, a
persistence action on a JPA entity, an http request, JDBC request and so on.
Controlling an event means applying some control mechanism which could be
security, monitoring, locking, archiving etc. and particularly dual control
principles.
If an event is controlled by Four-Eyes it is not executed but stored and
postponed. Only when a second authenticated user gives his okay (release),
the event is executed. Cibet allows also for example to give different
permissions for the same method call: The first user has permission to
invoke it, but not to release it, the second user has permission to release
it. 

Authentication and Authorization is outside of scope of Cibet, we don’t want
to reinvent the wheel. We did already integration with Spring Security
(which by the way was much harder to accomplish than integration with Shiro
and did cost some more Jira issues) and now with Shiro. The use case where
we have this problem is with a special dual control mechanism:  Two-Man-Rule
<http://en.wikipedia.org/wiki/Two-man_rule>  . In addition to Four-Eyes,
here the two users must be present at the same time. That means they must
both be authenticated and authorized in the same thread/session. A use case
could look like this:

-	A user is logged in in an application and executes something
-	Cibet detects that this event is controlled by Two-Man-Rule and informs
the application that the event is postponed
-	The application proposes a dialogue to the user for a second login. This
must be different to the first one.
-	Cibet delegates to the security framework (Shiro, Spring Security) to
authenticate the second user. Its subject is stored not in the first user’s
session but in the Cibet context
-	Cibet delegates permission check of the second user to the security
framework and executes the event if okay.

As Cibet is a framework we should not make assumptions on the embedding
application. Also we don’t want to force the application developer to make a
special Shiro configuration (a special SecurityManager for example) or do a
configuration ourselves. In the framework we can make configurations only
programmatically. That’s why I prefer to use only the interfaces.

I see now only two possibilities:
-	Split the login method into authentication and storing the Subject in the
interface. This is how it is done in Spring Security. However, this would
fray out the clean interface and make it more complicated for ‘normal’ users
of Shiro. This is not acceptable.
-	Like I showed in my last email use a CibetSecurityManager which relies on
DefaultSecurityManager that does not save the Subject. I can catch
ClassCastException and output a big warning, that this method does not work
if a custom SecurityManager is used and must be overridden accordingly.

best regards Wolfgang



--
View this message in context: http://shiro-user.582556.n2.nabble.com/Shiro-Integration-in-Cibet-framework-tp7577945p7577955.html
Sent from the Shiro User mailing list archive at Nabble.com.