如何在Shiro中注册AuthenticationListener

时间:2013-11-20 15:51:15

标签: guice shiro

登录,注销 - 一切正常但我不知道如何注册AuthenticationListener来记录我的用户。

我正在与Guice合作,我正在使用自己的DBSaltAwareRealm(公共类DBSaltAwareRealm扩展AuthorizingRealm)

THX

2 个答案:

答案 0 :(得分:2)

好的,我找到了另一个解决方案:

<强> 1。像往常一样初始化你的Guice-Modules:

public class ConfigServeletWithGuice extends GuiceServletContextListener {
    ...

    @Override
    protected Injector getInjector() {
        final Injector injector = Guice.createInjector(new ServeletModule(), new BusinessLogicModule(),
                new AuthenticationModule(_ctx), new ShiroAopModule(), ShiroWebModule.guiceFilterModule());

        final SecurityManager securityManager = injector.getInstance(SecurityManager.class);
        SecurityUtils.setSecurityManager(securityManager);

        logger.debug("Creation of Injector - done!");

        return injector;
    }
}

<强> 2。创建自己的SecurityManager:

public class MyWebSecurityManager extends DefaultWebSecurityManager {
    @SuppressWarnings("unused")
    private static Logger logger = LoggerFactory.getLogger(MyWebSecurityManager.class.getSimpleName());

    @Inject
    private AuthenticationListener authenticationListener;

    public MyWebSecurityManager() {
        super();
    }

    @SuppressWarnings({"UnusedDeclaration"})
    public MyWebSecurityManager(Realm singleRealm) {
        this();
        setRealm(singleRealm);
    }

    @SuppressWarnings({"UnusedDeclaration"})
    public MyWebSecurityManager(Collection realms) {
        this();
        setRealms(realms);
    }

    @Override
    protected void onSuccessfulLogin(final AuthenticationToken token, final AuthenticationInfo info, final Subject subject) {
        super.onSuccessfulLogin(token, info, subject);

        logger.debug("onSuccessfulLogin");
        authenticationListener.onSuccess(token, info);
    }

    @Override
    protected void onFailedLogin(final AuthenticationToken token, final AuthenticationException ae, final Subject subject) {
        super.onFailedLogin(token, ae, subject);

        logger.debug("onFailedLogin");
        authenticationListener.onFailure(token,ae);
    }

    @Override
    protected void beforeLogout(final Subject subject) {
        super.beforeLogout(subject);

        logger.debug("beforeLogout");
        authenticationListener.onLogout(subject.getPrincipals());
    }
}

第3。最后,绑定您自己的SecurityManager:

public class AuthenticationModule extends ShiroWebModule {
    static Logger logger = LoggerFactory.getLogger(AuthenticationModule.class.getSimpleName());

    public AuthenticationModule(final ServletContext sc) {
        super(sc);
    }

    @SuppressWarnings("unchecked")
    @Override
    protected void configureShiroWeb() {
        logger.debug("Start to configure ShiroWeb...");

        bind(AuthenticationListener.class).to(AuthenticationListenerImpl.class);
        ...
        logger.debug("configuration ShiroWeb - done!");
    }

    @Override
    // !!!!!! Here it comes:
    protected void bindWebSecurityManager(final AnnotatedBindingBuilder bind) {
        try {
            bind.toConstructor(MyWebSecurityManager.class.getConstructor(Collection.class)).asEagerSingleton();
        } catch (NoSuchMethodException e) {
            throw new ConfigurationException("This really shouldn't happen.  Either something has changed in Shiro, or there's a bug in ShiroModule.", e);
        }
    }
}

现在,重新启动后,您应该会看到您的日志消息!

答案 1 :(得分:2)

以下是我在shiro项目中修改samples-guice中的SampleShiroServletModule的方法:

public class SampleShiroServletModule extends ShiroWebModule {

    @Override
protected void configureShiroWeb() {
    ....

    final Multibinder<AuthenticationListener> listenerMultibinder = Multibinder.newSetBinder(binder(), AuthenticationListener.class);
    listenerMultibinder.addBinding().to(MyAuthenticationListener.class);

}

@Override
protected void bindWebSecurityManager(final AnnotatedBindingBuilder<? super WebSecurityManager> bind) {
    bind.to(DefaultWebSecurityManager.class);
}

@Provides
DefaultWebSecurityManager provideDefaultSecurityManager(final Collection<Realm> realms, final Set<AuthenticationListener> authenticationListeners) {
    DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager(realms);
    ModularRealmAuthenticator authenticator = new ModularRealmAuthenticator();
    authenticator.setAuthenticationListeners(authenticationListeners);
    securityManager.setAuthenticator(authenticator);
    return securityManager;
}

}