tk.my batis 는 어떻게 자신의 유 니 버 설 mapper 를 확장 합 니까?
18131 단어 tk.mybatismapper
목적:tk.my batis 가 제공 하 는 유 니 버 설 mapper 는 사용 하기에 편리 하지만 일부 sql 에 서 는 우리 의 수 요 를 만족 시 키 지 못 합 니 다.또한 우 리 는 deleted 문 구 를 관리 하고 싶 습 니 다(유 니 버 설 mapper 가 제공 하 는 것 은 물리 적 삭제 이기 때문에 가끔 민감 한 데 이 터 를 논리 적 으로 삭제 할 수 밖 에 없습니다).따라서 우 리 는 기 존의 유 니 버 설 mapper 를 바탕 으로 자신의 확장 을 진행 할 것 입 니 다.
1 jar 도입
<!-- springboot -->
<dependency>
<groupId>tk.mybatis</groupId>
<artifactId>mapper</artifactId>
<version>3.4.0</version>
</dependency>
이 가방
<!-- springboot -->
<dependency>
<groupId>tk.mybatis</groupId>
<artifactId>mapper-spring-boot-starter</artifactId>
<version>2.0.2</version>
</dependency>
springboot 프로젝트 는 이 가방 을 직접 인용 합 니 다.이번 에는 springboot 를 기반 으로 개발 할 것 입 니 다.jar 패키지 버 전 을 주의 하 십시오.너무 낮은 버 전에 문제 가 생 길 수 있 습 니 다.다음 에 소개 하 겠 습 니 다.2 설정 클래스 작성
package com.example.configuration;
import com.example.common.mapper.commonMapper.CommonMapper;
import org.mybatis.spring.boot.autoconfigure.MybatisAutoConfiguration;
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import tk.mybatis.spring.mapper.MapperScannerConfigurer;
import java.util.Properties;
@Configuration
@AutoConfigureAfter(MybatisAutoConfiguration.class)
public class MyBatisConfiguration {
@Bean
public MapperScannerConfigurer mapperScannerConfigurer() {
MapperScannerConfigurer mapperScannerConfigurer = new MapperScannerConfigurer();
mapperScannerConfigurer.setSqlSessionFactoryBeanName("sqlSessionFactory");
mapperScannerConfigurer.setBasePackage("com.example.dao.mapper");
Properties properties = new Properties();
properties.setProperty("mappers", CommonMapper.class.getName());
properties.setProperty("notEmpty", "false");
properties.setProperty("identity", "MYSQL");
properties.setProperty("order","BEFORE");
mapperScannerConfigurer.setProperties(properties);
return mapperScannerConfigurer;
}
}
여 기 는 두 가 지 를 주의해 야 한다.1>CommonMapper 이것 은 우리 가 정의 한 유 니 버 설 mapper 입 니 다.단독 가방 아래 에 놓 습 니 다.즉,이 가방 아래 에 이 mapper 만 있 습 니 다.그렇지 않 으 면 우 리 는 실 용적 인 팬 형 을 사용 할 때 유형 전환 문제 가 발생 할 수 있 습 니 다.(나 는 이곳 에서 오랫동안 고민 했다)
2>사용자 정의 mapper 스 캔 경 로 를 설정 합 니 다.springboot 프로젝트 는 jar 패키지 버 전 을 주의해 야 합 니 다.버 전이 너무 낮 으 면 설정 류 에서 의 정 의 는 소 용이 없습니다.스 캔 이 안 되 는 지 제 가 예전 에 사 용 했 던 버 전 1,2,3 에 이 문제 가 발생 할 것 입 니 다.더 높 은 버 전 으로 바 꾸 면 해결 할 수 있 습 니 다.
3 일반적인 방법 인 터 페 이 스 를 사용자 정의 Mapper 인터페이스 에 통합 합 니 다.
저 희 는 my sql 데이터 베 이 스 를 사용 하기 때문에 유 니 버 설 기능 을 사용 할 때 자주 사용 하 는 방법 을 선택 적 으로 도입 합 니 다.다음은 자신 이 정의 하 는 자주 사용 하 는 mapper 류 의 통합 입 니 다.이 기본 클래스 는 BasePackage 의 경로 에 두 지 마 십시오.이 경로 의 mapper 는 모두 명확 한 범 형 형식 을 지정 해 야 합 니 다.
1>조회 기능 제공 Mapper:
package com.example.common.mapper.basics;
import tk.mybatis.mapper.common.Marker;
import tk.mybatis.mapper.common.base.select.*;
import tk.mybatis.mapper.common.condition.SelectByConditionMapper;
import tk.mybatis.mapper.common.condition.SelectCountByConditionMapper;
import tk.mybatis.mapper.common.example.SelectByExampleMapper;
import tk.mybatis.mapper.common.ids.SelectByIdsMapper;
/**
* @desc mapper
*
*/
public interface SelectMapper<T> extends Marker,
SelectOneMapper<T>,
tk.mybatis.mapper.common.base.select.SelectMapper<T>,
SelectAllMapper<T>,
SelectCountMapper<T>,
SelectByPrimaryKeyMapper<T>,
ExistsWithPrimaryKeyMapper<T>,
SelectByIdsMapper<T>,
SelectByConditionMapper<T>,
SelectCountByConditionMapper<T>,
SelectByExampleMapper<T> {
}
2>추가 기능 mapper 제공
package com.example.common.mapper.basics;
import tk.mybatis.mapper.common.Marker;
import tk.mybatis.mapper.common.MySqlMapper;
import tk.mybatis.mapper.common.base.insert.InsertSelectiveMapper;
/**
* @desc mapper
*/
public interface InsertMapper<T> extends Marker,
tk.mybatis.mapper.common.base.insert.InsertMapper<T>,
InsertSelectiveMapper<T>,
MySqlMapper<T>{
}
3>업데이트 기능 mapper 제공
package com.example.common.mapper.basics;
import tk.mybatis.mapper.common.Marker;
import tk.mybatis.mapper.common.base.update.UpdateByPrimaryKeyMapper;
import tk.mybatis.mapper.common.base.update.UpdateByPrimaryKeySelectiveMapper;
import tk.mybatis.mapper.common.condition.UpdateByConditionMapper;
import tk.mybatis.mapper.common.condition.UpdateByConditionSelectiveMapper;
import tk.mybatis.mapper.common.example.UpdateByExampleSelectiveMapper;
/**
* @desc mapper
*
*/
public interface UpdateMapper<T> extends Marker,
UpdateByPrimaryKeyMapper<T>,
UpdateByPrimaryKeySelectiveMapper<T>,
UpdateByConditionMapper<T>,
UpdateByConditionSelectiveMapper<T>,
UpdateByExampleSelectiveMapper<T> {
}
4>삭제 기능 mapper 제공
package com.example.common.mapper.basics;
import com.example.common.mapper.defined.DeleteShamByIdsMapper;
import tk.mybatis.mapper.common.Marker;
import tk.mybatis.mapper.common.base.delete.DeleteByPrimaryKeyMapper;
import tk.mybatis.mapper.common.condition.DeleteByConditionMapper;
import tk.mybatis.mapper.common.ids.DeleteByIdsMapper;
/**
* @desc mapper
*
*/
public interface DeleteMapper<T> extends Marker,
tk.mybatis.mapper.common.base.delete.DeleteMapper<T>,
DeleteByPrimaryKeyMapper<T>,
DeleteByConditionMapper<T>,
DeleteByIdsMapper<T>{
}
5>첨삭 검사 의 기본 클래스 CommonMapper 제공
package com.example.common.mapper.commonMapper;
import com.example.common.mapper.basics.DeleteMapper;
import com.example.common.mapper.basics.InsertMapper;
import com.example.common.mapper.basics.SelectMapper;
import com.example.common.mapper.basics.UpdateMapper;
/**
* @param <T>
* @desc mapper
*/
public interface CommonMapper<T> extends
DeleteMapper<T>,
InsertMapper<T>,
SelectMapper<T>,
UpdateMapper<T> {
}
6>실체 대상
package com.example.dao.entity;
import lombok.Data;
import javax.persistence.Id;
import javax.persistence.Table;
import java.io.Serializable;
@Table(name="user")
@Data
public class User implements Serializable {
@Id
private Integer id;
private String trueName;
private String userName;
private Integer isDeleted;
}
7>사용자 정의 mapper 가 CommenMapper 를 계승 하도록 하면 이 문 구 를 사용 할 수 있 습 니 다.
package com.example.dao.mapper;
import com.example.common.mapper.commonMapper.CommonMapper;
import com.example.dao.entity.User;
public interface UserMapper extends CommonMapper<User> {
}
다음은 CommonMapper 에서 삭제 방법 을 제공 하 는 DeleteMapper 를 강화 하여 논리 적 으로 삭제 하 는 문 구 를 추가 할 것 입 니 다.1>사용자 정의 Provider 는 MapperTemplate 를 계승 하고 구조 방법 을 복사 해 야 합 니 다.
이것 은 원본 코드 의 대량 삭제 입 니 다.
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by Fernflower decompiler)
//
package tk.mybatis.mapper.provider;
import java.util.Set;
import org.apache.ibatis.mapping.MappedStatement;
import tk.mybatis.mapper.MapperException;
import tk.mybatis.mapper.entity.EntityColumn;
import tk.mybatis.mapper.mapperhelper.EntityHelper;
import tk.mybatis.mapper.mapperhelper.MapperHelper;
import tk.mybatis.mapper.mapperhelper.MapperTemplate;
import tk.mybatis.mapper.mapperhelper.SqlHelper;
public class IdsProvider extends MapperTemplate {
public IdsProvider(Class<?> mapperClass, MapperHelper mapperHelper) {
super(mapperClass, mapperHelper);
}
public String deleteByIds(MappedStatement ms) {
Class<?> entityClass = this.getEntityClass(ms);
StringBuilder sql = new StringBuilder();
sql.append(SqlHelper.deleteFromTable(entityClass, this.tableName(entityClass)));
Set<EntityColumn> columnList = EntityHelper.getPKColumns(entityClass);
if (columnList.size() == 1) {
EntityColumn column = (EntityColumn)columnList.iterator().next();
sql.append(" where ");
sql.append(column.getColumn());
sql.append(" in (${_parameter})");
return sql.toString();
} else {
throw new MapperException(" deleteByIds [" + entityClass.getCanonicalName() + "] @Id ");
}
}
public String selectByIds(MappedStatement ms) {
Class<?> entityClass = this.getEntityClass(ms);
this.setResultType(ms, entityClass);
StringBuilder sql = new StringBuilder();
sql.append(SqlHelper.selectAllColumns(entityClass));
sql.append(SqlHelper.fromTable(entityClass, this.tableName(entityClass)));
Set<EntityColumn> columnList = EntityHelper.getPKColumns(entityClass);
if (columnList.size() == 1) {
EntityColumn column = (EntityColumn)columnList.iterator().next();
sql.append(" where ");
sql.append(column.getColumn());
sql.append(" in (${_parameter})");
return sql.toString();
} else {
throw new MapperException(" selectByIds [" + entityClass.getCanonicalName() + "] @Id ");
}
}
}
다음 에 우 리 는 IdsProvider 를 확장 해서 그 로 하여 금 대량 논리 삭 제 를 지원 하 게 한다1>IdsdProvider 의 하위 클래스 만 들 기
package com.example.common.mapper.defined;
import org.apache.ibatis.mapping.MappedStatement;
import tk.mybatis.mapper.MapperException;
import tk.mybatis.mapper.entity.EntityColumn;
import tk.mybatis.mapper.mapperhelper.EntityHelper;
import tk.mybatis.mapper.mapperhelper.MapperHelper;
import tk.mybatis.mapper.mapperhelper.SqlHelper;
import tk.mybatis.mapper.provider.IdsProvider;
import java.util.Set;
public class IdsProviderDefined extends IdsProvider {
public IdsProviderDefined(Class<?> mapperClass, MapperHelper mapperHelper) {
super(mapperClass, mapperHelper);
}
public String deleteShamByIds(MappedStatement ms) {
Class<?> entityClass = this.getEntityClass(ms);
StringBuilder sql = new StringBuilder();
sql.append(SqlHelper.updateTable(entityClass, this.tableName(entityClass)));
sql.append("<set> is_deleted='1' </set>");
Set<EntityColumn> columnList = EntityHelper.getPKColumns(entityClass);
if (columnList.size() == 1) {
EntityColumn column = (EntityColumn)columnList.iterator().next();
sql.append(" where ");
sql.append(column.getColumn());
sql.append(" in (${_parameter})");
return sql.toString();
} else {
throw new MapperException(" deleteByIds [" + entityClass.getCanonicalName() + "] @Id ");
}
}
}
deleteShamByIds 는 바로 우리 문 에서 대량으로 논리 적 으로 삭제 하 는 방법 입 니 다.이 방법 은 바로 sql 을 재 조립 하 는 것 입 니 다.tk 에서 sql 을 조립 하 는 데 도움 을 주 고 매개 변수 클래스(SqlHelper,EntityHelper)를 많이 제공 합 니 다.우 리 는 사용 할 수 있 습 니 다.2>DeleteShamByIdsMapper 인터페이스 만 들 기
package com.example.common.mapper.defined;
import org.apache.ibatis.annotations.DeleteProvider;
public interface DeleteShamByIdsMapper<T> {
@DeleteProvider(
type = IdsProviderDefined.class,
method = "dynamicSQL"
)
int deleteShamByIds(String var1);
// IdsProviderDefined
}
3>deleteMapper 에서 사용자 정의 논리 삭제 인 터 페 이 스 를 계승 합 니 다 deleteShamByIdsMapper
package com.example.common.mapper.basics;
import com.example.common.mapper.defined.DeleteShamByIdsMapper;
import tk.mybatis.mapper.common.Marker;
import tk.mybatis.mapper.common.base.delete.DeleteByPrimaryKeyMapper;
import tk.mybatis.mapper.common.condition.DeleteByConditionMapper;
import tk.mybatis.mapper.common.ids.DeleteByIdsMapper;
/**
* @desc mapper
*
*/
public interface DeleteMapper<T> extends Marker,
tk.mybatis.mapper.common.base.delete.DeleteMapper<T>,
DeleteByPrimaryKeyMapper<T>,
DeleteByConditionMapper<T>,
DeleteByIdsMapper<T>,
DeleteShamByIdsMapper<T>{
}
여기에서 사용자 정의 대량 논리 삭 제 를 정의 하면 유 니 버 설 마 퍼 를 확장 할 수 있 습 니 다.TK my batis 플러그 인 유 니 버 설 mapper 와 Oacle 의 구덩이
최근 회사 에 서 는 몇 가지 프로젝트 의 데이터 베 이 스 를 사용 하 는 Oacle 이 있 습 니 다.한동안 사용 하지 않 았 다가 과감하게 구덩이 에 빠 졌 습 니 다.몇 가 지 를 기록 하 는 것 이 대표 적 입 니 다.
1:Oacle 의 대량 데이터 삽입 에 대해 서 는 TK 유 니 버 설 mapper 의 insertList 방법 으로 자동 으로 연 결 된 sql 이 이 렇 습 니 다.
insert into table(column1,column2)values
(value1,value2),
(value3,value4)。。。
어떻게 보면 문제 가 없 을 까?그리고 sql 이 정확하게 끝나 지 않 았 다 고 계속 보고 했다.자신의 sql 에 대한 지나친 자신 감 때문에 매개 변수 문제 인지 생각 하고 몇 시간 을 낭비 했다.나중에 sql 을 잘 맞 춰 서 데이터 베 이 스 를 잃 어 버 리 고 뛰 었 더 니 이런 sql 은 Oacle 에서 뛸 수 없다 는 것 을 알 게 되 었 다.Oacle 에서 대량으로 삽입 하 는 문법 은 다음 과 같 아야 한다.
INSERT ALL
INTO A(field_1,field_2) VALUES (value_1,value_2)
INTO A(field_1,field_2) VALUES (value_3,value_4)
INTO A(field_1,field_2) VALUES (value_5,value_6)
TK 코드 를 대충 살 펴 보 니 데이터베이스 드라이버 를 검사 하지 않 고 바로 sql 을 맞 추기 시작 한 것 같 습 니 다.
public String insertList(MappedStatement ms) {
Class<?> entityClass = this.getEntityClass(ms);
StringBuilder sql = new StringBuilder();
sql.append(SqlHelper.insertIntoTable(entityClass, this.tableName(entityClass)));
sql.append(SqlHelper.insertColumns(entityClass, true, false, false));
sql.append(" VALUES ");
sql.append("<foreach collection=\"list\" item=\"record\" separator=\",\" >");
sql.append("<trim prefix=\"(\" suffix=\")\" suffixOverrides=\",\">");
Set<EntityColumn> columnList = EntityHelper.getColumns(entityClass);
Iterator var5 = columnList.iterator();
while(var5.hasNext()) {
EntityColumn column = (EntityColumn)var5.next();
if (!column.isId() && column.isInsertable()) {
sql.append(column.getColumnHolder("record") + ",");
}
}
sql.append("</trim>");
sql.append("</foreach>");
return sql.toString();
}
그러나 저 는 이런 플러그 인 은 호 환 방안 이 있 을 것 이 라 고 생각 합 니 다.그리고 이 플러그 인 을 사용 한 것 은 원본 my batis 를 사용 하 는 것 과 충돌 하지 않 기 때문에 실제 개발 에 영향 을 주지 않 습 니 다.Oacle 의 기 초 를 복습 하고 자신 에 게 일 깨 워 주 는 셈 입 니 다.프로그래머 는 성실 하 게 먼저 실행 하고 독선 적 인 경험 도 가끔 씩 함정 에 빠 집 니 다.2:oracle 에 대한 비교 기호(<>=)와 null
일단 복습 을 해 보도 록 하 겠 습 니 다.
일반 데이터베이스 에서 특정한 필드 가 비어 있 거나 비어 있 지 않 을 때 is null 또는 is not null 을 사용 합 니 다.
검색 조건 사용=null 또는<>null 은 데 이 터 를 찾 을 수 없습니다.
그러나 할당 은 사용 할 수 있 습 니 다.
update BUS_PLATFORM.bus_trans set return_code = null where return_msg= 'tac ';
이것 은 성공 적 으로 실행 할 수 있 습 니 다.그러나 이것 은 모두 표 밖의 값 조작 입 니 다.그러면 표 안의 데이터 가 null 이 있 을 때 어떤 구덩이 가 있 습 니까?예 를 들 어.
select * from table1 where name <>'zhansan'
조회 표 의 name 필드 는 zhangsan 의 데이터 가 아 닙 니 다.표 에 name 이 null 인 데이터 가 있 을 때 이 데 이 터 는 찾 을 수 없습니다.예 를 들 어 표 에 100 개의 데이터 가 있 고 한 데이터 의 name 값 은 zhangsan 이 며 9 개의 데이터 의 name 값 은 null 입 니 다.그러면 이 sql 은 90 개의 데이터 만 찾 을 수 있 습 니 다.따라서 정확 한 수요 가 있 으 면 name 값 이 zhangsan 이 아 닌 데 이 터 를 조회 하고 name 값 이 null 인 데 이 터 를 포함 하면 sql 은
select * from table1 where name <>'zhansan' or name is null
3:이것 은 my batis 의 규범 입 니 다.기본적으로 숫자 를 채 우 는 것 이지 만 저 를 함정 에 빠 뜨 린 적 이 있 습 니 다.먼저 내용:my batis 가 null 값 을 삽입 할 때 이 값 의 형식(jdbctype)을 지정 해 야 합 니 다.그렇지 않 으 면 오류 가 발생 할 수 있 습 니 다.
형식 을 지정 하지 않 으 면 my batis 는 일치 하 는 데이터베이스 필드 형식 을 스스로 맞 출 수 있 기 때문에 null 은 적합 하지 않 습 니 다.어쩌면 잘못 을 보고 할 지도 모 르 니 매우 확실 하 다.그러나 일반적으로 xml 로 sql 을 설정 하면 이 문제 가 발생 하지 않 습 니 다.쓸 때 편 하 게 적 습 니 다.이것 도 제 가 TK 를 사용 할 때 드 러 난 문제 입 니 다.insert 방법 을 사용 할 때 null 이 있 으 면 끊 습 니 다.하지만 TK 는 insert Selective 방법 으로 삽입 할 때 자동 으로 빈 값 을 걸 러 냅 니 다.
이상 은 개인 적 인 경험 이 므 로 여러분 에 게 참고 가 되 기 를 바 랍 니 다.여러분 들 도 저 희 를 많이 응원 해 주시 기 바 랍 니 다.
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
tk.my batis 는 어떻게 자신의 유 니 버 설 mapper 를 확장 합 니까?목적:tk.my batis 가 제공 하 는 유 니 버 설 mapper 는 사용 하기에 편리 하지만 일부 sql 에 서 는 우리 의 수 요 를 만족 시 키 지 못 합 니 다.또한 우 리 는 deleted 문 구 를 관...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.