2009-11-02 5 views
12

My Java (JDK6) 프로젝트는 모든 데이터베이스 액세스에 SpringJDBCTemplate을 사용합니다. 우리는 최근 Spring 2.5에서 Spring 3 (RC1)로 업그레이드했습니다. 프로젝트는 Hibernate 또는 EJB과 같은 ORM을 사용하지 않습니다. 여러 (오버로드) 방법이있는 것처럼자바 프로그래밍 - 스프링 및 JDBCTemplate - query, queryForList 또는 queryForRowSet을 사용 하시겠습니까?

내가 기록의 무리를 읽고, 그들과 함께 내부 처리가 필요한 경우, 그것은 보인다 쿼리, queryForList 및 queryForRowSet

하나를 사용하도록 기준이 될해야합니까 다른 대신에? 성능 차이가 있습니까? 모범 사례?

이 주제에 대한 추가 조사를 위해 외부 참조를 권할 수 있습니까? 당신은 멋진 제네릭 땅에 있기 때문에

답변

34

목록으로 액세스하는 표준 방법은 다른 방법이 아닌 query() 방법을 사용하는 것입니다. query과 다른 메소드의 가장 큰 차이점은 콜백 인터페이스 (RowMapper, RowCallbackHandler 또는 ResultSetExtractor) 중 하나를 구현하여 결과 세트를 처리해야한다는 것입니다.

RowMapper은 대부분 시간을 사용하여 자신을 발견 할 가능성이 높습니다. 결과 집합의 각 행이 목록의 한 객체에 해당 할 때 사용됩니다. 행에 들어가는 객체 유형을 채우고 반환하는 단일 메소드 mapRow 만 구현하면됩니다. Spring은 BeanPropertyRowMapper을 가지고 있는데 이는 bean 프라퍼티 이름을 컬럼 이름 (이 클래스는 성능이 아닌 편의를위한 것임)과 일치시킴으로써리스트의 객체들을 채울 수있다.

RowCallbackHandler은 단순한 목록 이상의 결과가 필요한 경우에 더 유용합니다. 이 접근법을 사용하고있는 반환 객체를 직접 관리해야합니다. 보통 반환 형식 (즉, 트리 테이블의 그룹화 된 데이터 또는 기본 키를 기반으로 사용자 지정 캐시를 만드는 경우)로지도 구조가 필요할 때이 방법을 사용하고 있습니다.

ResultSetExtractor은 결과의 반복을 제어하려는 경우에 사용됩니다. query에 대한 호출의 반환 값이 될 단일 메서드 extractData을 사용합니다. 다른 콜백 인터페이스 중 하나를 사용하여 빌드하기에 더 복잡한 사용자 정의 데이터 구조를 작성해야하는 경우에만이를 사용합니다.

queryForList() 메서드는 이러한 콜백 메서드를 구현할 필요가 없다는 점에서 유용합니다. queryForList를 사용하는 두 가지 방법이 있습니다. 첫 번째는 데이터베이스에서 단일 열 (예 : 문자열 목록) 만 쿼리하는 경우 클래스를 인수로 사용하는 메서드 버전을 사용하여 해당 클래스의 개체 목록을 자동으로 제공 할 수 있습니다 .

queryForList()의 다른 구현을 호출하면 각 항목이 각 열의지도 인 목록이 다시 표시됩니다. 콜백 메소드 작성에 드는 비용을 절감 할 수 있다는 장점이 있지만이 데이터 구조를 다루는 것은 상당히 어렵습니다. 지도의 값이 Object이므로 많은 양의 캐스팅을 할 것입니다.

실제로 야생에서 사용 된 queryForRowSet 개의 방법을 본 적이 없습니다. 그러면 쿼리의 전체 결과가 Spring SqlRowSet에 의해 포착 된 CachedRowSet 개체로로드됩니다. SqlRowSet을 응용 프로그램의 다른 레이어로 전달할 경우이 레이어를 데이터 액세스 구현에 연결한다는 점에서이 객체를 사용할 때 큰 단점이 있습니다.

BeanPropertyRowMapper으로 언급 한 것 외에는 이러한 호출간에 성능 차이가 크게 나타나지 않습니다. 대규모 결과 집합을 복잡한 조작으로 작업하는 경우 특정 상황에 맞게 최적화 된 ResultSetExtractor을 작성하여 성능을 향상시킬 수 있습니다.

자세히 알아 보려면 Spring JDBC documentationJavaDoc for the classes I've mentioned을 참조하십시오. 또한 Spring Framework의 일부 책을 살펴볼 수도있다. 약간 날짜가 있긴하지만 Java Development with the Spring Framework은 JDBC 프레임 워크 작업에 대한 아주 좋은 섹션을 가지고 있습니다. 무엇보다도, 나는 각 방법마다 약간의 코드를 작성하고 무엇이 가장 잘 작동하는지 보려고한다.

3

은, 당신이 정말 수행 할 수 있습니다 것은 SimpleJdbcTemplate를 사용하여 개별 개체에 대한 개체의 ListsqueryForObject() 자사 query() 방법을 사용하는 것입니다. 이것에 대한 추론은 단순히 JdbcTemplate에있는 것보다 사용하기가 쉽다는 것입니다.

+1

AFIK Java 5 호환 쿼리 메서드는 SpringTemplate과 Spring 3에서 사용할 수 있습니다. – Adrian

+1

JdbcTemplate은 Spring 2.5.6에서는 Generics를 사용하지 않지만 3.0.0에서는 확인했습니다. 나는 앞으로 deprecation을 냄새가납니다. :) – Esko

+0

SimpleJdbcTemplate은 이제 참으로 사용되지 않습니다 – Helenesh

2

위의 우수한 답변에 작은 추가 사항 : 간단한 쿼리를 실행하고 단일 행을 예상하는 경우 queryForInt, queryForLong, queryForMap, queryForObject 등과 같은 추가 메소드가 때때로 좋은 옵션처럼 보일 수 있습니다.

그러나 0 또는 1 행을 다시 가져올 수있는 경우 queryForList 메서드가 일반적으로 더 쉽습니다. 그렇지 않으면 IncorrectResultSizeDataAccessException을 catch해야합니다. 나는 어려운 길을 배웠다.