Есть много начинающих Java, которые мало знают о Mybatis Interceptor Inteceptor. Здесь я организую следующую статью, чтобы вы могли объяснить Inteceptor Mybatis Inteceptor в Java.
В этой статье в основном анализируется механизм плагина Mybatis, который на самом деле является реализацией модели цепочки ответственности Java Dynamic Proxy.
Согласно официальной документации. Mybatis позволяет только перехватывать следующие методы, которые определяют параметры подписи аннотации перехвата.
Код выглядит следующим образом
Исполнитель (обновление, запрос, промывка, коммит, откат, getTransaction, Close, Isclose) ParameterHandler (getParameterObject, SetParameters) ResultsEthandler (Handleresultssets, HangeoutputParameters)
Исходный код обработки перехватчика заключается в следующем, где InterceptorChain.pluginall (..) - это пользовательское плетение перехвата:
Код выглядит следующим образом
/ * Метод в org.apache.ibatis.session.configuration class */public parameterhandler newparameterhandler (отображение Statatement MappedStatement, объект ParameterObject, BoundsQl Boundsql) {ParameterHandler ParameterHandler = mapedStatement.getLang (). CreateParameterHandler (mavedStatement, parameterObjemement.get -getLang (). CreateParameterHandler (mavedStatement, parameterObjectement.getSquemement. /* Parameter -handler*/ parameterHandler = (parameterHandler) receptorChain.pluginall (parameterHandler); return parameterHandler;}public ResultSetHandler newResultSetHandler(Executor executor, MappedStatement mappedStatement, RowBounds rowBounds, ParameterHandler parameterHandler, ResultHandler resultHandler, BoundSql boundSql) { ResultSetHandler resultSetHandler = new DefaultResultSetHandler(executor, mappedStatement, parameterHandler, resultHandler, Boundsql, Rowbounds); /* Перехватить результатыэндлер*/ resultsethandler = (resultsethandler) receptorchain.pluginall (resulthandler); return resultSetHandler;}public StatementHandler newStatementHandler(Executor executor, MappedStatement mappedStatement, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) { StatementHandler statementHandler = new RoutingStatementHandler(executor, mappedStatement, parameterObject, rowBounds, resultHandler, Boundsql); /* Intercept ratporthandler*/ ratementhandler = (atportion handler) receptorchain.pluginall (ratporthandler); return atportionHandler;} public Executor newexeCutor (транзакция транзакции, executortype exectortype) {rececuTortype = executortype == null? defaultexecutortype: executortype; executortype = executortype == null? Exectortype.simple: executype; Исполнитель исполнителя; if (exectortype.batch == executortype) {experator = new batchexecutor (это, транзакция); } else if (recemortype.reuse == rexortortype) {rececutor = new reuseexecutor (это, транзакция); } else {executor = new SimpleExecutor (this, transaction); } if (cacheenabled) {executor = new cachingexecutor (исполнитель); } /* Recement recepator* / receector = (исполнитель) receptorChain.pluginall (Исполнитель); return Executor;} Чтобы реализовать пользовательский перехватчик, вам нужно только реализовать интерфейс Interceptor. Общий код выглядит следующим образом:
Код выглядит следующим образом
/* Метод и параметры аннотации, которые указывают, какой интерфейс для перехвата*/ @recepts ({@signature (type = ratementhandler.class, method = "prepare", args = {connection.class})}) public class yourInterceptor реализует Interceptor {public Object invocation invocation) {dosemptore (); / * Примечание. Здесь метод vocation.proceed () фактически используется для завершения прохождения вызовов цепочки InterceptorChain (то есть для выполнения всех зарегистрированных методов перехвата перехватчика) и исходного вызова метода окончательного объекта прокси */ return vocation.proceed (); } / * Сгенерировать прокси для целевой цели, и аннотация @Intercepts используется в плагине Plugin.Wrap * / @Override Public Object (объект Target) { / * Когда целевой класс имеет тип оператора handler, целевой класс обернут, и не используется бессмысленный прокси * / return (Target InstactionOf handler)? Plugin.Rap (Target, Target, Target): Target; } /* Используется для установки пользовательских параметров конфигурации перехвата* / @Override public void setProperties (свойства свойств) {}} Среди них код для перехвата вызовов находится в plugin.wrap:
Код выглядит следующим образом
/* org.apache.ibatis.plugin.plugin class*/public plugin plugin vlocationhandler {/* Опустить код ...*/public Static Object (цель объекта, Interceptor Interceptor) {/* ЗДЕСЬ для получения аннотации Signature Interceptor*/map <?>, set <Method >> signatureMap = getSignatoreR (interceptor); Класс <?> Type = target.getClass (); /* Получить интерфейс, соответствующий целевому классу*/ class <?> [] Interfaces = getallinterfaces (type, signatureMap); if (interfaces.length> 0) { /* Использовать jdk dynamic proxy* / return proxy.newproxyinstance (type.getclassloader (), интерфейсы, новый плагин (Target, Interceptor, SignatureMap)); } return Target; } /* Выполнение всех методов целевого класса перехвата будет выполнено здесь* / @override public Object volue Invoke (объект прокси, метод метода, объект [] args) бросает throwable {try {set <method> = signaturemap.get (method.getDeclaringclass ()); if (methods! = null && methods.contains (method)) { /* Выполнить метод перехвата* / return receptor.intercept (new Invocation (target, method, args)); } method return.invoke (target, args); } catch (Exception e) {throw ExceptionUtil.UnWrapThrowable (e); }} / * Опустить код ... * /}Вы можете видеть, что основной код дизайна Mybatis Interceptor относительно прост, но он достаточно гибкий. При использовании его на практике будьте осторожны, чтобы не быть бессмысленным прокси (плагин.wrap).