在很多时候,我们都需要将一些关键的日志信息保存到数据库中,而此时Spring aop能够较灵活的解决这一问题,并不带有侵入性。关于spring aop的介绍,网上有不少文章进行介绍,在这里就略去这一点,本文将重点介绍AOP记录日志的配置方法。
1.利用maven创建一个web工程
pom.xml
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.cxc</groupId>
<artifactId>springaop</artifactId>
<packaging>war</packaging>
<version>1.0-SNAPSHOT</version>
<name>springaop Maven Webapp</name>
<url>http://maven.apache.org</url>
<properties>
<!-- version setting -->
<spring.version>3.2.5.RELEASE</spring.version>
<slf4j.version>1.7.5</slf4j.version>
<log4j.version>1.2.17</log4j.version>
<commons-lang3.version>3.1</commons-lang3.version>
<commons-io.version>2.4</commons-io.version>
<commons-codec.version>1.8</commons-codec.version>
<!-- other setting -->
<jdk.version>1.7</jdk.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<downloadSources>false</downloadSources>
</properties>
<dependencies>
<dependency>
<groupId>jdk.tools</groupId>
<artifactId>jdk.tools</artifactId>
<version>1.7</version>
<scope>system</scope>
<systemPath>${JAVA_HOME}/lib/tools.jar</systemPath>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId>
<version>1.7.5</version>
</dependency>
<dependency>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
<version>1.1.1</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
<version>2.5</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.1</version>
<scope>provided</scope>
</dependency>
<!-- spring -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${spring.version}</version>
<exclusions>
<exclusion>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
<version>${spring.version}</version>
<exclusions>
<exclusion>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>${spring.version}</version>
</dependency>
<!-- AOP begin -->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjrt</artifactId>
<version>1.7.4</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.7.4</version>
</dependency>
<dependency>
<groupId>cglib</groupId>
<artifactId>cglib</artifactId>
<version>3.1</version>
<scope>runtime</scope>
</dependency>
<!-- AOP end -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>${spring.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.5</version>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<finalName>springaop</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>${jdk.version}</source>
<target>${jdk.version}</target>
<encoding>UTF-8</encoding>
</configuration>
</plugin>
</plugins>
</build>
</project>
2.Java Web目录结构
此demo只是为了说明实现方式,请忽略其中的层次结构和命名规范。
MyLog.java类很简单,主要实现执行的方法名的显示及此方法的第1个参数值。在实际应用中我们可将这些信息存入DB中。
package com.cxc.log;
import org.aspectj.lang.JoinPoint;
public class MyLog {
public void doLog(JoinPoint joinPoint) {
String method = joinPoint.getSignature().getName();
// System.out.println("方法名:" + method);
Object[] args = joinPoint.getArgs();
if (args != null && args.length > 0) {
System.out.println(method+":"+args[0]);
}
}
}
User.java为用户信息实体类。复写了toString方法。
public class User {
private String id;
private String username;
private int age;
private String remarks;
public User(String id, String username, int age, String remarks) {
super();
this.id = id;
this.username = username;
this.age = age;
this.remarks = remarks;
}
……
}
IUserService.java主要是对用户信息的CRUD操作接口。
package com.cxc.user.service;
import com.cxc.user.bean.User;
public interface IUserService {
public void save(User user);
public void delete(String id);
public void update(User user);
public void query();
}
UserSerivce.java则实现IUserService接口,每个方法体中打印出各自的方法。
@Service
public class UserService implements IUserService{
@Override
public void save(User user) {
System.out.println("save user");
}
@Override
public void delete(String id) {
System.out.println("delete user");
}
@Override
public void update(User user) {
System.out.println("update user");
}
@Override
public void query() {
System.out.println("query user");
}
}
3.ApplicationContext.xml配置
主要是实现在Service包下的所有方法执行前执行MyLog.java中的doLog方法。
<context:component-scan base-package="com.cxc"></context:component-scan>
<tx:annotation-driven />
<aop:config>
<aop:aspect id="logAspect" ref="aspectLog">
<!--配置com.spring.service包下所有类或接口的所有方法 -->
<aop:pointcut id="jLog" expression="execution(* com.cxc.*.service.**.*(..))" />
<aop:before pointcut-ref="jLog" method="doLog" />
<!-- <aop:after-throwing pointcut-ref="jLog" method="doThrowing" throwing="ex"
/> -->
</aop:aspect>
</aop:config>
<bean id="aspectLog" class="com.cxc.log.MyLog" />
4.测试
需要注意的是若使用以下注解的配置方式,需要的Junit版本为4.5+
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:applicationContext.xml")
public class UserTest extends AbstractJUnit4SpringContextTests {
@Autowired
IUserService userService;
@Test
public void testSave() {
userService.save(new User("1","cxc0716",25,"备注"));
}
}
执行结果:
这样,简单的基本Spring aop的日志记录功能到此结束。