gpt4 book ai didi

java - 无法在自定义 Apache Shiro AuthorizingRealm 中 @Inject 我的 DAO

转载 作者:塔克拉玛干 更新时间:2023-11-01 21:40:22 27 4
gpt4 key购买 nike

我正在尝试将我的 UserDAO 注入(inject)到 Apache Shiro 正在使用的自定义 AuthorizingRealm 中,但是......我得到了 null。

我做错了什么?

shiro.ini

[main]
user = demo.shiro.security.FacesAjaxAwareUserFilter
realmA = demo.shiro.security.JpaRealm
credentialsMatcher = org.apache.shiro.authc.credential.SimpleCredentialsMatcher
realmA.credentialsMatcher = $credentialsMatcher
securityManager.realms = $realmA
user.loginUrl = /pages/public/login.xhtml

[users]
admin = admin
user = user

[urls]
# public files and folders
/index.html = anon
/resources/** = anon
/pages/public/** = anon

# restricted files and folders
/pages/admin/** = user
/pages/user/** = user

JpaRealm.java

public class JpaRealm extends AuthorizingRealm {

@Inject
private UserDao userDao;

public JpaRealm() {
setCredentialsMatcher(new Sha256CredentialsMatcher());
}

protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authToken) throws AuthenticationException {
UsernamePasswordToken token = (UsernamePasswordToken) authToken;
User user = userDao.getForUsername(token.getUsername());
if (user != null) {
return new SimpleAuthenticationInfo(user.getId(), user.getPassword(), getName());
} else {
return null;
}
}

protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
Long userId = (Long) principals.fromRealm(getName()).iterator().next();
User user = userDao.findByKey(userId);
if (user != null) {
SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
for (Role role : user.getRoles()) {
info.addRole(role.getDescription());
for (Permition permition : role.getPermitions()) {
info.addStringPermission(permition.getDescription());
}
}
return info;
} else {
return null;
}
}

}

我必须做什么才能让 CDI 知道我的自定义领域内的 @Inject 并正确地注入(inject)我的 UserDAO?

最佳答案

Apache Shiro 使用的默认 EnvironmentLoaderListener 不是 CDI 感知的。解决方案是构建一个并替换 web.xml 中的原始引用以指向您的自定义引用。

注意: listeners automatically 支持 CDI 注入(inject),但监听器必须通过 CDI 机制请求 bean。自定义监听器将使用 @Inject 请求 bean,并将创建 JpaRealm 作为 CDI bean,这将注入(inject)所有依赖项。默认的 Shire 监听器不会通过 @Inject 创建 JpaRealm 作为启用 CDI 的 bean。

CustomCredentialsMatcher.java

public class CustomCredentialsMatcher extends SimpleCredentialsMatcher {
}

CustomEnvironmentLoaderListener.java

public class CustomEnvironmentLoaderListener extends EnvironmentLoaderListener {

@Inject
private JpaRealm jpaRealm;

@Override
protected WebEnvironment createEnvironment(ServletContext pServletContext) {
WebEnvironment environment = super.createEnvironment(pServletContext);
RealmSecurityManager rsm = (RealmSecurityManager) environment.getSecurityManager();
PasswordService passwordService = new DefaultPasswordService();
PasswordMatcher passwordMatcher = new PasswordMatcher();
passwordMatcher.setPasswordService(passwordService);
jpaRealm.setCredentialsMatcher(passwordMatcher);
rsm.setRealm(jpaRealm);
((DefaultWebEnvironment) environment).setSecurityManager(rsm);
return environment;
}

}

FacesAjaxAwareUserFilter.java

public class FacesAjaxAwareUserFilter extends UserFilter {

private static final String FACES_REDIRECT_XML = "<?xml version=\"1.0\" encoding=\"UTF-8\"?><partial-response><redirect url=\"%s\"></redirect></partial-response>";

@Override
protected void redirectToLogin(ServletRequest req, ServletResponse res) throws IOException {
HttpServletRequest request = (HttpServletRequest) req;

if ("partial/ajax".equals(request.getHeader("Faces-Request"))) {
res.setContentType("text/xml");
res.setCharacterEncoding("UTF-8");
res.getWriter().printf(FACES_REDIRECT_XML, request.getContextPath() + getLoginUrl());
} else {
super.redirectToLogin(req, res);
}
}

}

JpaRealm.java

public class JpaRealm extends AuthorizingRealm {

private static String REALM_NAME = "jpaRealm";

@Inject
private UserDao userDao;

@Inject
private RoleDao roleDao;

@Inject
private PermissionDao permissionDao;

public JpaRealm() {
setName(REALM_NAME); // This name must match the name in the User class's getPrincipals() method
}

protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authToken) throws AuthenticationException {
UsernamePasswordToken token = (UsernamePasswordToken) authToken;
User user = userDao.getForUsername(token.getUsername());
if (user != null) {
return new SimpleAuthenticationInfo(user.getId(), user.getPassword(), getName());
} else {
return null;
}
}

protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
Long userId = (Long) principals.fromRealm(getName()).iterator().next();
User user = userDao.findByKey(userId);
if (user != null) {
SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
for (Role role : roleDao.getForUser(user)) {
info.addRole(role.getDescription());
for (Permition permition : permissionDao.getForRole(role)) {
info.addStringPermission(permition.getDescription());
}
}
return info;
} else {
return null;
}
}

}

shiro.ini

[main]
user = com.boss.mrfoods.security.FacesAjaxAwareUserFilter
user.loginUrl = /pages/public/login.xhtml

[urls]
/index.html = anon
/pages/index.xhtml = anon
/pages/public/** = anon

/pages/admin/** = user, roles[ADMIN]
/pages/user/** = user, roles[USER]

网络.xml

...

<listener>
<listener-class>com.boss.mrfoods.security.CustomEnvironmentLoaderListener</listener-class>
</listener>

<filter>
<filter-name>ShiroFilter</filter-name>
<filter-class>org.apache.shiro.web.servlet.ShiroFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>ShiroFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
...

关于java - 无法在自定义 Apache Shiro AuthorizingRealm 中 @Inject 我的 DAO,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15605038/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com