개발/java

jpa 흉내내기

캐리캐리 2024. 10. 23. 11:36

1탄 

https://ehhooni.tistory.com/32

 

mybatis로 jpa 흉내내기

mybatis의 경우 jdbc를 통해 코드와 db를 혼합하여 작성하는 방식에서 둘을 분리하게 구현함으로써 유지 보수 및 개발을 함에 있어 간편하고 쉽게 만들었다 그 이후 JPA가 도입됨에 따라  DB table에

ehhooni.tistory.com

 

1탄 select 버젼에 이어 insert도 가능합니다.

 

mybatis는 insert의 경우 new SQL().INSERT_INFO를 이용하여 동적으로 생성이 가능하다 

NEW SQL().INSERT_INFO(테이블명)
.INTO_COLUMNS(컬럼명들..)
.INTO_VALUES(컬럼값들 ..)

 

앞서 예시에서 나온 클래스인 OrderInfo를 토대로 한번 작성을 해보자 

class MyBatisProvider implements ProviderMethodResolver {

  public static String findById(String id) {
    -- 위 링크 참조
  }
  public String insertById(ProviderContext context , T t){
  	Map<String , Object> map = new ObjectMapper().getMapper().convertValue(T,Map.class);
    Map<String ,String> insertMap = new HashMap<>();
    map.forEach((key,value) ->{
    	/*cf) class 내 annotation을 통해 컬럼명을 지정해놓았다면 이와 같은 방식으로 쓸 수 있다.
          Field field = FieldUtils.getField(OrderInfo.class, key, true);
        if(Objects.nonNull(value) && field.isAnnotationPresent(RdbColumn.class)){
        	insertMap.put(field.getAnnotation(RdbColumn.class).name(),value);
        }  
        */
    	if(Objects.nonNull(value)){
        	insertMap.put(key,"#{".concat(key)+"}");
        }
    })
    
  	String sql = new SQL().INSERT_INFO(this.tableName(context))
    .INTO_COLUMNS(insertMap.keySet().stream().toArray(String[]::new))
    .INTO_VALUES(insertMap.values().stream().toArray(String[]::new));
    
    
    return sql;
  } 
}

 

 

이제 이를 사용하고자 하는 Mapper에 연결만 하면 insert는 동적으로 생성이 가능하다 

 

@Dao
public interface OrderInfoMapper extends MybatisMapper<OrderInfo, RequestModel> {
}

public interface MybatisMapper<T,  ID extends Serializable> {
	@SelectProvider(type = MyBatisSqlProvider.class)
    List<T> findById(ID id);
    
    //method이름이 동일하다면 별도 이름을 작성할 필요가 없다 
    @InsertProvider(type = MyBatisSqlProvider.class , method = "insertById")
    void insertById(T model);
}

 

 

이제 사용하고자하는 곳에서 주입받아서 method를 불러만 온다면 요청하는 테이블에 데이터들이 삽입이 될 것이다. 

 

@Autowired 
OrderInfoMapper orderInfoMapper;

void test(){
	OrderInfo orderInfo = new OrderInfo();
    
    orderInfoMapper.insertById(orderInfo);/
}