I haven't tried this myself, but what I would do is extend
FormAuthenticationFilter. Then, override "redirectToLogin".
In this method, simply send the 401 response code. Something like this:
protected void redirectToLogin(ServletRequest request,
ServletResponse response) {
if (log.isDebugEnabled()) {
log.debug("Authentication required: sending 401
Authentication challenge response.");
}
HttpServletResponse httpResponse = WebUtils.toHttp(response);
httpResponse.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
}
Note, you will now have to configure your filter as the one in your
filter chain, rather than "authc".
-Jared
On Thu 03 Nov 2011 07:09:08 AM CDT, Bengt Rodehav wrote:
> Jared and Eduard,
>
> Thanks for both your responses. The Vaadin example is interesting but
> I cannot change to Vaadin at this point. However, moving away from
> BasicAuthentication to form based authentication seems like the right
> move for me. I've tested it a bit and got it working but I have one
> problem:
>
> The default behaviour in Shiro (when using "authc") seems to be
> redirection to a login page. I want to change this behaviour so that
> the HTTP status code 401 is returned instead. My Ajax application can
> then intercept this error code and prompt the user to login without
> leaving the page. How can I accomplish this?
>
> /Bengt
>
> 2011/11/2 Eduard Neuwirt <[email protected]
> <mailto:[email protected]>>
>
> Am 02.11.2011 19:00, schrieb Jared Bunting:
>
> On Wed 02 Nov 2011 10:57:13 AM CDT, Bengt Rodehav wrote:
>
> Thanks a lot for your quick reply Jared.
>
> I tried to return a 401 but it doesn't seem to cause the
> web browser
> (Firefox in this case) to drop the user and password from
> its cache.
> If I do a refresh then the cached user is automatically
> re-authenticated again.
>
> Very annoying...
>
> We're developing an Ajax application which is the reason
> why we don't
> want to redirect to a specific login page (that could use
> form based
> login). If the user actively logs out then it's OK to
> redirect to a
> login page but if the session times out, then we want to
> stay on the
> same page so that the user can continue working after
> having specified
> its user and password again.
>
> Basic authentication is not a requirement for me but it
> seemed like an
> easy way to avoid redirecting to a dedicated login page.
> Is there a
> way to accomplish an "ajax login" using Shiro? Is there a best
> practice for it?
>
> Thanks,
>
> /Bengt
>
>
> 2011/11/2 Jared Bunting<jared.bunting@__peachjean.com
> <mailto:[email protected]>
> <mailto:jared.bunting@__peachjean.com
> <mailto:[email protected]>>>
>
> On Wed 02 Nov 2011 09:52:24 AM CDT, Bengt Rodehav wrote:
> > I'm using Shiro together with the http service in
> Apache Karaf which
> > in turn uses Jetty under the hood. I use Shiro 1.1.
> >
> > I've created my own AuthorizingRealm since we have
> a legacy system
> > that I redirect the authentication to. This seems
> to work and I can
> > get the currently logged in user as follows:
> >
> > Subject subject = SecurityUtils.getSubject();
> >
> > When calling the "isAuthenticated" method I can see
> that the user is
> > logged in.
> >
> > However, on each call from the web browser to my
> web application, a
> > new authentication is being made. This means that I
> can't really log
> > out the user neither explicitly nor by session
> timeout. If I call
> >
> > subject.logout()
> >
> > I can see that the user is indeed logged out since
> "isAuthenticated"
> > then returns false. But on the next request from
> the web browser the
> > user is authenticated again and a new session is
> created. If I
> restart
> > the web browser then I have to login again but as
> long as the web
> > browser is running the user seems to be automatically
> > re-authenticated. I use basic authentication and
> the behaviour
> is the
> > same in both Chrome and Firefox.
> >
> > Obviously I haven't understood how these things
> work. Can anyone
> > explain to me how I can log out a user both
> explicitly and via
> session
> > timeout?
> >
> > /Bengt
>
> If I understand what you're describing correctly, you
> are running into
> a browser behavior. Typically, when using HTTP BASIC
> authentication,
> the browser will cache the user's name and password,
> and send the auth
> header with every single request. This is very useful
> behavior for
> stateless webapps that require authentication. It's
> less useful when
> you're already tracking a known user.
>
> Unfortunately, I know of no way to alter this
> behavior. One thing you
> could try is, when logging a user out, return a 401.
> This should
> cause
> the browser to re-ask the user for a
> username/password, which they
> could cancel. So, while that's the best that I can
> offer, it sounds
> like a crappy UI.
>
> If you have a page-based, user-navigable webapp, you
> might consider
> using form authentication instead of basic. It avoids
> this issue
> completely.
>
> Sorry I could not be of more help.
>
> -Jared
>
>
> I haven't done it, but it seems like you could do something in
> ajax to
> ask for username/password (popup, ajaxified appearing form, or
> something of that nature) and submit that to the login page.
> Shiro
> form authentication doesn't force the user to go to the login
> page - it
> mostly just wants a post to that page with the
> username/password fields.
>
> -Jared
>
> Hi,
>
> it is not exactly what you want, but rather similar.
>
>
> http://eneuwirt.de/2011/04/22/__using-apache-shiro-to-secure-__vaading-application/
>
> <http://eneuwirt.de/2011/04/22/using-apache-shiro-to-secure-vaading-application/>
>
> Vaadin is Ajax based
>
> Regards
> Eduard
>
>