In einigen Java-Projekten wird MapperScannerConfigurer bei der Integration von Mybatis und Spring verwendet. Diese Klasse generiert automatisch schnittstellenbasierte dynamische Proxy-Klassen über Reverse-Proxy.
Vor diesem Hintergrund analysiert dieser Artikel kurz den dynamischen Proxy von Java.
In diesem Artikel wird ein dynamischer Proxy verwendet, um einen Interceptor zu simulieren, der Transaktionen abwickelt.
Schnittstelle:
öffentliche Schnittstelle UserService { public void addUser(); public void searchUser();}Implementierungsklasse:
public class UserServiceImpl implementiert UserService { public void addUser() { System.out.println("add user"); public void removeUser() { System.out.println("remove user"); System.out.println("search user" }}Es gibt zwei Möglichkeiten, einen dynamischen Java-Proxy zu implementieren
1. Der dynamische Proxy, der mit JDK geliefert wird
Um den mit jdk gelieferten dynamischen Proxy zu verwenden, müssen Sie die InvocationHandler-Schnittstelle und die Proxy-Klasse verstehen. Beide befinden sich im Paket java.lang.reflect.
Einführung in den InvocationHandler:
InvocationHandler ist die vom Aufrufhandler der Proxy-Instanz implementierte Schnittstelle.
Jeder Proxy-Instanz ist ein InvocationHandler zugeordnet. Beim Aufrufen einer Methode auf einer Proxy-Instanz ruft diese Methode die Invoke-Methode des InvocationHandler auf.
Proxy-Einführung:
Proxy bietet statische Methoden zum Erstellen dynamischer Proxy-Klassen und -Instanzen.
Beispiel (Simulation der AOP-Transaktionsverarbeitung):
öffentliche Klasse TransactionInterceptor implementiert InvocationHandler { private Object target; public void setTarget(Object target) { this.target = target } @Override public Object invoke(Object Proxy, Method method, Object[] args) throws Throwable { System.out.println ("start Transaction"); method.invoke(target, args); System.out.println("end Transaction");Testcode:
öffentliche Klasse TestDynamicProxy { @Test public void testJDK() { TransactionInterceptor TransactionInterceptor = new TransactionInterceptor(); UserService userService = new UserServiceImpl(); UserService userServiceProxy = (UserService) Proxy.newProxyInstance( userService.getClass() .getClassLoader(), userService.getClass().getInterfaces(), TransactionInterceptor); userServiceProxy.addUser(}}Testergebnisse:
Transaktion starten, Benutzer hinzufügen und Transaktion beenden
Wenn wir einen Methodenaufruf über die Proxy-Klasse userServiceProxy durchführen, wird die Transaktion natürlich vor und nach dem Methodenaufruf geöffnet und geschlossen.
2. Bibliothek cglib eines Drittanbieters
CGLIB ist eine leistungsstarke, leistungsstarke und qualitativ hochwertige Codegenerierungsbibliothek zur Erweiterung von Java-Klassen und zur Implementierung von Java-Schnittstellen zur Laufzeit.
Der größte Unterschied zum dynamischen Proxy von JDK ist:
Der dynamische JDK-Proxy ist für Schnittstellen gedacht, während cglib einen Proxy für Klassen implementiert. Das Prinzip von cglib besteht darin, eine Unterklasse für die angegebene Zielklasse zu generieren und die Methoden zu überschreiben, um eine Erweiterung zu erreichen vertreten.
Der Beispielcode lautet wie folgt:
öffentliche Klasse UserServiceCallBack implementiert MethodInterceptor { @Override public Object intercept(Object o, Method method, Object[] args, MethodProxy methodProxy) throws Throwable { System.out.println("start Transaction by cglib"); methodProxy.invokeSuper(o, args ); System.out.println("end Transaction by cglib");Testcode:
public class TestDynamicProxy { @Test public void testCGLIB() { Enhancer Enhancer = new Enhancer(); raiser.setSuperclass(UserServiceImpl.class(new UserServiceCallBack()); ; Proxy.addUser();Testergebnisse:
starte die Transaktion von cglibadd userend die Transaktion von cglib
Interessierte Leser können die Beispiele in diesem Artikel tatsächlich testen, und ich glaube, sie werden viel gewinnen.