Acegi是基于Spring的一个开源的安全认证框架,现在的最新版本是1.04。Acegi的特点就是有很多的过滤器:不过我们也用不到这么多的过滤器,只是可以把它们看作为一个个的模块,在用的时候加上自己用的着的即可,由于认证的流程的方面比较复杂导致它的配置很复杂,如果能摸清它的工作原理还是不太难.
先下载acegi http://sourceforge.net/projects/acegisecurity/包并解压得到.jar包,放入lib目录。在web.xml中配置如下:
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
version="2.5">
<display-name>Struts Blank</display-name>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:applicationContext.xml</param-value>
</context-param>
<filter>
<filter-name>Acegi Filter Chain Proxy</filter-name>
<filter-class>org.acegisecurity.util.FilterToBeanProxy</filter-class>
<init-param>
<param-name>targetClass</param-name>
<param-value>org.acegisecurity.util.FilterChainProxy</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>Acegi Filter Chain Proxy</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter>
<filter-name>struts2</filter-name>
<filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<welcome-file-list>
<welcome-file>index.jsp</welcome-file>
</welcome-file-list>
</web-app>
在applicationContext-acegisecurity.xml 中的配置如下:(注意:它的XML头必须的如下<beans>中为空,不然会出现异常)
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
<bean id="filterChainProxy" class="org.acegisecurity.util.FilterChainProxy">
<property name="filterInvocationDefinitionSource">
<value><![CDATA[
CONVERT_URL_TO_LOWERCASE_BEFORE_COMPARISON
PATTERN_TYPE_APACHE_ANT
/**=httpSessionContextIntegrationFilter,logoutFilter,authenticationProcessingFilter,securityContextHolderAwareRequestFilter,rememberMeProcessingFilter,anonymousProcessingFilter,exceptionTranslationFilter,filterInvocationInterceptor
]]></value>
</property>
</bean>
<bean id="httpSessionContextIntegrationFilter"
class="org.acegisecurity.context.HttpSessionContextIntegrationFilter" />
<bean id="logoutFilter" class="org.acegisecurity.ui.logout.LogoutFilter">
<constructor-arg value="/index.jsp" /> <!-- URL redirected to after logout -->
<constructor-arg>
<list>
<ref bean="rememberMeServices" />
<bean class="org.acegisecurity.ui.logout.SecurityContextLogoutHandler" />
</list>
</constructor-arg>
</bean>
<!-- 提交表单时,用到的过滤器 -->
<bean id="authenticationProcessingFilter"
class="org.acegisecurity.ui.webapp.AuthenticationProcessingFilter">
<property name="authenticationManager" ref="authenticationManager" />
<!-- 当认证失败时,跳转到login_error.jsp页面 -->
<property name="authenticationFailureUrl" value="/login_error.jsp" />
<property name="defaultTargetUrl" value="/" />
<!-- 提交表单时,要验证的地址 -->
<property name="filterProcessesUrl" value="/j_acegi_security_check" />
<property name="rememberMeServices" ref="rememberMeServices" />
</bean>
<bean id="securityContextHolderAwareRequestFilter"
class="org.acegisecurity.wrapper.SecurityContextHolderAwareRequestFilter" />
<bean id="rememberMeProcessingFilter"
class="org.acegisecurity.ui.rememberme.RememberMeProcessingFilter">
<property name="authenticationManager" ref="authenticationManager" />
<property name="rememberMeServices" ref="rememberMeServices" />
</bean>
<bean id="anonymousProcessingFilter"
class="org.acegisecurity.providers.anonymous.AnonymousProcessingFilter">
<property name="key" value="changeThis" />
<property name="userAttribute" value="anonymousUser,ROLE_ANONYMOUS" />
</bean>
<bean id="exceptionTranslationFilter" class="org.acegisecurity.ui.ExceptionTranslationFilter">
<property name="authenticationEntryPoint">
<bean
class="org.acegisecurity.ui.webapp.AuthenticationProcessingFilterEntryPoint">
<property name="loginFormUrl" value="/login_error.jsp" /><!--得到登录表单的信息 -->
<property name="forceHttps" value="false" /><!--不用https -->
</bean>
</property>
<property name="accessDeniedHandler">
<bean class="org.acegisecurity.ui.AccessDeniedHandlerImpl">
<property name="errorPage" value="/accessDenied.jsp" /><!--授权失败的时抛出异常 转向的网页 -->
</bean>
</property>
</bean>
<bean id="filterInvocationInterceptor"
class="org.acegisecurity.intercept.web.FilterSecurityInterceptor">
<property name="authenticationManager" ref="authenticationManager" />
<property name="accessDecisionManager">
<bean class="org.acegisecurity.vote.AffirmativeBased">
<property name="allowIfAllAbstainDecisions" value="false" />
<property name="decisionVoters">
<list>
<bean class="org.acegisecurity.vote.RoleVoter" />
<bean class="org.acegisecurity.vote.AuthenticatedVoter" />
</list>
</property>
</bean>
</property>
<property name="objectDefinitionSource"><!-- 把URL和可访问的用户组对应起来 -->
<value><![CDATA[
CONVERT_URL_TO_LOWERCASE_BEFORE_COMPARISON<!-- 把URL全部转化为小写 -->
PATTERN_TYPE_APACHE_ANT <!-- 以ANT的形式来配置路径 -->
/login/admin/**=ROLE_SUPERVISOR
/login/**=IS_AUTHENTICATED_REMEMBERED
/**=IS_AUTHENTICATED_ANONYMOUSLY
]]></value>
</property>
</bean>
<bean id="rememberMeServices"
class="org.acegisecurity.ui.rememberme.TokenBasedRememberMeServices">
<property name="userDetailsService" ref="userDetailsService" />
<property name="key" value="changeThis" />
</bean>
<bean id="authenticationManager" class="org.acegisecurity.providers.ProviderManager">
<property name="providers">
<list>
<ref local="daoAuthenticationProvider" />
<bean
class="org.acegisecurity.providers.anonymous.AnonymousAuthenticationProvider">
<property name="key" value="changeThis" />
</bean>
<bean
class="org.acegisecurity.providers.rememberme.RememberMeAuthenticationProvider">
<property name="key" value="changeThis" />
</bean>
</list>
</property>
</bean>
<bean id="daoAuthenticationProvider"
class="org.acegisecurity.providers.dao.DaoAuthenticationProvider">
<property name="userDetailsService" ref="userDetailsService" />
</bean>
<!--
UserDetailsService is the most commonly frequently Acegi Security
interface implemented by end users
-->
<bean id="userDetailsService" class="org.acegisecurity.userdetails.jdbc.JdbcDaoImpl">
<property name="usersByUsernameQuery">
<value>select username,password,enabled from users where username=?
</value>
</property>
<property name="authoritiesByUsernameQuery">
<value>select username,authority from authorities where username=?
</value>
</property>
<property name="dataSource">
<ref local="dataSource" />
</property>
</bean>
<bean id="dataSource"
class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName">
<value>com.mysql.jdbc.Driver</value>
</property>
<property name="url">
<value>jdbc:mysql://localhost:3306/user</value>
</property>
<property name="username">
<value>root</value>
</property>
<property name="password">
<value>123</value>
</property>
</bean>
<!--
This bean is optional; it isn't used by any other bean as it only
listens and logs
-->
<bean id="loggerListener" class="org.acegisecurity.event.authentication.LoggerListener" />
</beans>
参考http://www.javaeye.com/topic/43341
mail的配置:在applicationContext-mail.xml中的配置:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd">
<!--
Application context definition for PetClinic on Hibernate.
-->
<beans>
<!-- 注意:这里的参数(如用户名、密码)都是针对邮件发送者的 -->
<bean id="mailSender" class="org.springframework.mail.javamail.JavaMailSenderImpl">
<property name="host">
<value>smtp.163.com</value>
</property>
<property name="javaMailProperties">
<props>
<prop key="mail.smtp.auth">true</prop>
<prop key="mail.smtp.timeout">25000</prop>
</props>
</property>
<property name="username">
<value>xxxx@163.com</value>
</property>
<property name="password">
<value>XXXX</value>
</property>
</bean>
</beans>
然后,我们用测试类来测试一下:
@Test
public void sendEmail() throws MessagingException {
// 获取上下文
ApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
// 获取JavaMailSender bean
JavaMailSender sender = (JavaMailSender) ctx.getBean("mailSender");
// SimpleMailMessage mail = new SimpleMailMessage(); // <SPAN
// style="COLOR: #ff0000">注意SimpleMailMessage只能用来发送text格式的邮件</SPAN>
// try {
// mail.setTo("xxxx@qq.com");// 接受者
// mail.setFrom("xxxx@163.com");// 发送者,这里还可以另起Email别名,不用和xml里的username一致
// mail.setSubject("ddd!");// 主题
// mail.setText("你好!dddd");// 邮件内容
// sender.send(mail);
// } catch (Exception e) {
// e.printStackTrace();
// }
JavaMailSenderImpl senderImpl = new JavaMailSenderImpl();
MimeMessage mailMessage = senderImpl.createMimeMessage();
//设置utf-8或GBK编码,否则邮件会有乱码
MimeMessageHelper messageHelper = new MimeMessageHelper(mailMessage,true,"utf-8");
try {
messageHelper.setTo("xxxx@qq.com");//接受者
messageHelper.setFrom("xxxxx@163.com");//发送者
messageHelper.setSubject("测试邮件");//主题
//邮件内容,注意加参数true
messageHelper.setText("hello!!chao.wang.k kjfjg分隔符看到看到了广泛的个个工商管理开发和水果看 ",true);
//附件内容
messageHelper.addInline("a", new File("E:/个人资料/派遣报到证号:.txt"));
messageHelper.addInline("b", new File("E:/个人资料/http_imgload.jpg"));
// File file=new File("E:/测试中文文件.rar");
// // 这里的方法调用和插入图片是不同的,使用MimeUtility.encodeWord()来解决附件名称的中文问题
// messageHelper.addAttachment(MimeUtility.encodeWord(file.getName()), file);
sender.send(mailMessage);
} catch (Exception e) {
e.printStackTrace();
}
}
简单应用就说完了