Analysis of spring boot + mybatis interceptor failure

Time:2021-9-2

1、 Environmental information
SpringBoot:2.3.6.RELEASE
Mybatis-plus:3.3.1
2、 Encounter problems
Today, due to the functional needs of the business system, the interceptor of mybatis is used to set the user’s current locale (NLS) for the Oracle database session_ Language), if the interceptor code does not take effect, it is hereby recorded for future reference.
3、 The code is as follows:
1. Add the following code to the @ configuration related code of mybatis (automatically injected into the interceptor chain):

/**
 *Change session state
 *
 * @return
 */
@Bean
public AlterSessionInterceptor alterSessionInterceptor() {
    return new AlterSessionInterceptor();
}

2. Interceptor code (intercept the prepare method of statementhandler, get the connection and execute the statement of alter session):
/**

  • <p>
  • Change session parser
  • </p>
    *
  • @since 2021/7/14
    */

@Slf4j
@Intercepts({@Signature(type = StatementHandler.class, method = “prepare“, args = {Connection.class, Integer.class})})
public class AlterSessionInterceptor implements Interceptor {

@Override
public Object intercept(Invocation invocation) throws Throwable {
    Object[] args = invocation.getArgs();
    Connection connection = (Connection) args[0];
    if ("Oracle".equalsIgnoreCase(connection.getMetaData().getDatabaseProductName())) {
        Statement statement = null;
        try {
            statement = connection.createStatement();
            String locale = RequestHelper.getCurrentLocale();
            if ("en_GB".equalsIgnoreCase(locale)) {
                statement.execute("ALTER SESSION SET NLS_LANGUAGE='AMERICAN'");
            } else {
                statement.execute("ALTER SESSION SET NLS_LANGUAGE='SIMPLIFIED CHINESE'");
            }
        } finally {
            statement.close();
        }
    }
    return invocation.proceed();
}

}
When running debugging, it is found that the code cannot execute the interception logic. After referring to the paging plug-in code, it is found that the following methods need to be overloaded (by default, the code only needs to implement the interface intercept, but in fact, it needs to add the processing logic of the following plug-in to enable the proxy of plugin):

@Override
public Object plugin(Object target) {
    if (target instanceof StatementHandler) {
        return Plugin.wrap(target, this);
    }
    return target;
}

The final interceptor code is as follows:
/**

  • <p>
  • Change session parser
  • </p>
    *
  • @since 2021/7/14
    */

@Slf4j
@Intercepts({@Signature(type = StatementHandler.class, method = “prepare”, args = {Connection.class, Integer.class})})
public class AlterSessionInterceptor implements Interceptor {

@Override
public Object intercept(Invocation invocation) throws Throwable {
    Object[] args = invocation.getArgs();
    Connection connection = (Connection) args[0];
    if ("Oracle".equalsIgnoreCase(connection.getMetaData().getDatabaseProductName())) {
        Statement statement = null;
        try {
            statement = connection.createStatement();
            String locale = RequestHelper.getCurrentLocale();
            if ("en_GB".equalsIgnoreCase(locale)) {
                statement.execute("ALTER SESSION SET NLS_LANGUAGE='AMERICAN'");
            } else {
                statement.execute("ALTER SESSION SET NLS_LANGUAGE='SIMPLIFIED CHINESE'");
            }
        } finally {
            statement.close();
        }
    }
    return invocation.proceed();
}

@Override
public Object plugin(Object target) {
    if (target instanceof StatementHandler) {
        return Plugin.wrap(target, this);
    }
    return target;
}

@Override
public void setProperties(Properties properties) {
    // to do nothing
}

}

Recommended Today

The selector returned by ngrx store createselector performs one-step debugging of fetching logic

Test source code: import { Component } from ‘@angular/core’; import { createSelector } from ‘@ngrx/store’; export interface State { counter1: number; counter2: number; } export const selectCounter1 = (state: State) => state.counter1; export const selectCounter2 = (state: State) => state.counter2; export const selectTotal = createSelector( selectCounter1, selectCounter2, (counter1, counter2) => counter1 + counter2 ); // […]