我很习惯使用Spring和Spring Security,但我无法弄清楚为什么这里依赖注入不起作用。 我有一个带有两个基本身份验证系统的应用程序,一个用于用户,一个用于两个管理员。这是security-context.xml:
<http use-expressions="true">
<intercept-url pattern="/" access="isAuthenticated()" />
<intercept-url pattern="/*" access="isAuthenticated()" />
<intercept-url pattern="/admin" access="hasRole('ROLE_ADMIN')" />
<intercept-url pattern="/admin/*" access="hasRole('ROLE_ADMIN')" />
<http-basic />
</http>
<beans:bean id="userDetailsServiceImpl"
class="com.foo.bar.service.LoginServiceImpl" />
<authentication-manager>
<authentication-provider user-service-ref="userDetailsServiceImpl" />
<authentication-provider>
<password-encoder hash="md5" />
<user-service>
<user name="AdminOne" password="eh223rh2efi9hfuwefugwg"
authorities="ROLE_ADMIN" />
<user name="AdminTwo" password="wdkjbcfwerjkbiwfviwefi"
authorities="ROLE_ADMIN" />
</user-service>
</authentication-provider>
</authentication-manager>
用户身份验证依赖于UserDetailsService的实现:
public class LoginServiceImpl implements UserDetailsService {
@Autowired
UserDetailsDAO dao;
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException, DataAccessException {
try {
// Get the credentials
return credentials;
} catch (NoResultException exc) {
throw new UsernameNotFoundException("username not found");
} catch (JDBCException jdbce) {
throw new DataAccessException("Cannot acess db", jdbce) {
private static final long serialVersionUID = 1L;
};
}
}
问题是字段UserDetailsDAO
为空。所以没有注射。奇怪的是,在测试环境中一切正常。并且在服务器启动期间不会抛出任何异常,这也很奇怪,因为通常会报告自动装配中的错误。
顺便说一句,管理员的身份验证就像一个魅力。
如果有用,这是web.xml: FOO
<servlet>
<servlet-name>Foo Dispatcher Servlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>
<!-- Here the context specific for a single project -->
/WEB-INF/spring/root-context.xml
/WEB-INF/spring/datasource-context.xml
</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>StreamViewer Dispatcher Servlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>
<!-- Here the context for all the projects -->
/WEB-INF/spring/security-context.xml
</param-value>
</context-param>
<filter>
<filter-name>springSecurityFilterChain</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
</filter>
<filter-mapping>
<filter-name>springSecurityFilterChain</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
答案 0 :(得分:1)
您应在<context:annotation-config />
中设置security-context.xml
以启用AutowiredAnnotationBeanPostProcessor,以设置@Autowired
带注释字段的值。
来自文档:
默认值 AutowiredAnnotationBeanPostProcessor将由。注册 “context:annotation-config”和“context:component-scan”XML标记。 如果您,请删除或关闭默认注释配置 打算指定一个自定义的AutowiredAnnotationBeanPostProcessor bean 定义
请参阅Is context:annotation-config an alternative to @AutoWired?
答案 1 :(得分:0)
如果要使用自动装配,则需要扫描bean而不是在xml文件中明确声明它们。
你应该替换
<beans:bean id="userDetailsServiceImpl"
class="com.foo.bar.service.LoginServiceImpl" />
使用:
<context:component-scan base-package="com.foo.bar" />
并使用以下命令注释您的LoginServiceImpl类:
@Service(name="userDetailsServiceImpl")