Mybatis — сопоставление параметров в классе QueryBuilder

Мне довольно удобно использовать mybatis в качестве инструмента ORM. Но я не могу понять, как работает сопоставление параметров в mybatis.

скажем, у меня есть определенный интерфейс mybatis mapper, у которого есть метод для получения сведений о пользователе.

И у меня определен мой Querybuilder класс, в котором есть выбор query.

public interface UserMapper {

    @SelectProvider(type = UserQueryBuilder.class, method = "getUserId")
    Long getUserId(@Param("first") String firstName, @Param("last") String lastName, @Param("location") String location);

}


public class UserQueryBuilder(){

    public String getUserId(String firstName, String lastName, String location) {
        return new SQL() {{
            SELECT("USER_TABLE.USER_ID");
            FROM("USER_TABLE");
            WHERE("USER_TABLE.FIRST_NAME" + " = #{first}");
            WHERE("USER_TABLE.LAST_NAME" + " = #{last}");
            WHERE("USER_TABLE.LOCATION" + " = #{location}");

        }}.toString();
    }

}

В упомянутом выше QueryBuilder показано, как параметры SQL-запроса могли быть сопоставлены с "первым" и "последним" значениями параметров, определенными в интерфейсе 'userMapper'.


person Siva Tharun    schedule 22.08.2018    source источник


Ответы (2)


MyBatis создает динамический прокси-сервер для сопоставителя, например Spring AOP Proxy для MyBatis используется MapperProxyFactory для создания экземпляра прокси-сервера MapperProxy с прокси-интерфейсом(UserMapper).

Поэтому при вызове getUserId MapperProxy перехватит целевой метод и параметры следующим образом:

public Object invoke(Object proxy, Method method, Object[] args) throws Throwable

это вызовет соответствующий MapperMethod для выполнения sql с преобразованными аргументами в параметры:

Object param = method.convertArgsToSqlCommandParam(args);
result = sqlSession.selectOne(command.getName(), param);

Поскольку method.convertArgsToSqlCommandParam на самом деле будет генерировать именованные параметры с помощью аннотаций @Param.

а также необходимо заменить placeholder(#{first}) на ask и с соответствующими параметрами, после этого он создаст BoundSql, которым принадлежит необработанный sql и параметры, они будут переданы jdbc dirver для выполнения, как если бы мы напрямую использовали jdbcTemplate.

person chengpohi    schedule 22.08.2018

Важно то, что UserQueryBuilder не получает параметры, определенные в интерфейсе UserMapper.

В выполнении запроса участвуют несколько компонентов:

  1. клиент картографа
  2. интерфейс картографа
  3. построитель запросов
  4. библиотека spring-mybatis
  5. библиотека mybatis

Назначение интерфейса картографа:

  1. чтобы указать запрос, который будет использоваться
  2. чтобы указать параметры, которые требуют запрос
  3. для определения фактического интерфейса Java

Mapper может определить запрос напрямую, используя аннотацию, такую ​​​​как @Select, неявно используя запрос, определенный в отображении xml, или используя построитель запросов через @SelectProvider. Назначение построителя такое же, как и у @Select или xml-маппинга, а именно provide the query text на маппер.

Фактическая реализация преобразователя обеспечивается файлом spring-mybatis. Эта реализация создается динамически на основе класса преобразователя. Реализация работает следующим образом: когда вызывается метод в преобразователе, он использует отражение для вызова соответствующих методов (таких как selectOne или selectList в зависимости от типа возвращаемого значения, определенного в методе преобразователя) в mybatis SqlSession. Для этого ему нужен текст запроса и параметры. Текст запроса берется из builder/annotation/xml. Параметры доступны в качестве параметров для вызова метода сопоставления. Затем SqlSessoin сам использует запрос и параметры для выполнения запроса с помощью JDBC API.

person Roman Konoval    schedule 22.08.2018