Guice AOP(进阶版)

本教程主要详细讲解Guice的一些AOP方式,通过该简单教程让我们可以快速使用Guice进行AOP开发,后续我们会更深入讲解更多Guice中的AOP.
基础环境

技术 版本
Java 1.8+
Guice 4.2.3
初始化项目
  • 初始化项目
mvn archetype:generate -DgroupId=io.edurt.lc.guice -DartifactId=guice-aop-senior -DarchetypeArtifactId=maven-archetype-quickstart -Dversion=1.0.0 -DinteractiveMode=false

  • 修改pom.xml增加Guice依赖
lc-guice io.edurt.lc.guice 1.0.0 4.0.0guice-aop-senior Learning Center for Guice AOP(Senior)1.8 1.8 com.google.inject guice 4.2.3 junit junit 4.12 test

初始化Service 首先我们定义服务Service,这个服务有一个简单的方法println.
  • src/main/java目录下新建io.edurt.lc.guice.GuiceAopSeniorService类文件,在文件输入以下内容
package io.edurt.lc.guice; import com.google.inject.ImplementedBy; import org.aopalliance.intercept.MethodInvocation; @ImplementedBy(value = https://www.it610.com/article/GuiceAopSeniorServiceImpl.class) public interface GuiceAopSeniorService { void before(MethodInvocation invocation); }

  • src/main/java目录下新建io.edurt.lc.guice.GuiceAopSeniorServiceImpl类文件,在文件输入以下内容
package io.edurt.lc.guice; import org.aopalliance.intercept.MethodInvocation; public class GuiceAopSeniorServiceImpl implements GuiceAopSeniorService { @Override public void before(MethodInvocation invocation) { System.out.println(String.format("Before method [%s]", invocation.getMethod().getName())); } }

AOP注入依赖 Guice允许在关联AOP之前将AOP的依赖都注入到容器中!
  • src/main/java目录下新建io.edurt.lc.guice.GuiceAopInjectionMethodInterceptor类文件,在文件输入以下内容
package io.edurt.lc.guice; import com.google.inject.Inject; import org.aopalliance.intercept.MethodInterceptor; import org.aopalliance.intercept.MethodInvocation; public class GuiceAopInjectionMethodInterceptor implements MethodInterceptor { @Inject private GuiceAopSeniorService service; @Override public Object invoke(MethodInvocation invocation) throws Throwable { service.before(invocation); Object response; try { response = invocation.proceed(); } finally { System.out.println(String.format("After [%s]", invocation.getMethod().getName())); } return response; } }

  • src/main/java目录下新建io.edurt.lc.guice.PrintlnService类文件,在文件输入以下内容
package io.edurt.lc.guice; import com.google.inject.ImplementedBy; @ImplementedBy(value = https://www.it610.com/article/PrintlnServiceImpl.class) public interface PrintlnService { void println(String input); }

  • src/main/java目录下新建io.edurt.lc.guice.PrintlnServiceImpl类文件,在文件输入以下内容
package io.edurt.lc.guice; import com.google.inject.name.Named; public class PrintlnServiceImpl implements PrintlnService { @Override @Named(value = "https://www.it610.com/article/println") public void println(String input) { System.out.println(input); } }

PrintlnServicePrintlnServiceImpl用于测试新的服务产出.
  • 接下来在src/test/java目录创建io.edurt.lc.guice.TestGuiceAopSenior类文件进行定义的服务进行测试,添加以下代码
package io.edurt.lc.guice; import com.google.inject.Guice; import com.google.inject.Inject; import com.google.inject.Injector; import com.google.inject.matcher.Matchers; import com.google.inject.name.Names; import org.junit.Test; public class TestGuiceAopSenior { @Inject private PrintlnService printlnService; @Test public void test() { Injector injector = Guice.createInjector(binder -> { GuiceAopInjectionMethodInterceptor injectionMethodInterceptor = new GuiceAopInjectionMethodInterceptor(); binder.requestInjection(injectionMethodInterceptor); binder.bindInterceptor(Matchers.any(), Matchers.annotatedWith(Names.named("println")), injectionMethodInterceptor); }); TestGuiceAopSenior application = injector.getInstance(TestGuiceAopSenior.class); application.printlnService.println("Hello Guice AOP"); } }

我们运行程序输出
Before method [println] Hello Guice AOP After [println]

需要注意的是:
binder.requestInjection(injectionMethodInterceptor); 该段代码用于注入自定义的AOP服务
binder.bindInterceptor(Matchers.any(), Matchers.annotatedWith(Names.named("println")), injectionMethodInterceptor); 这里的第二个参数不能使用 Matchers.any()否则会出现死循环,因为容器会不断的进行aop操作
源码地址 【Guice AOP(进阶版)】GitHub

    推荐阅读