Whiteship's Note

UserType만들기

Hibernate/Chapter 5 : 2008.02.04 17:18


클래스 구현하기

public class MonetaryAmountUserType implements UserType {

	public Object assemble(Serializable cached, Object owner)
			throws HibernateException {
		return cached;
	}

	public Object deepCopy(Object value) throws HibernateException {
		return value;
	}

	public Serializable disassemble(Object value) throws HibernateException {
		return (Serializable) value;
	}

	public boolean equals(Object x, Object y) throws HibernateException {
		if (x == y)
			return true;
		if (x == null || y == null)
			return false;
		return x.equals(y);
	}

	public int hashCode(Object x) throws HibernateException {
		return x.hashCode();
	}

	public boolean isMutable() {
		return false;
	}

	public Object nullSafeGet(ResultSet resultSet, String[] names, Object owner)
			throws HibernateException, SQLException {

		BigDecimal valueInUSD = resultSet.getBigDecimal(names[0]);
		if (resultSet.wasNull())
			return null;

		// DB에서 가져온 다음에 원하는 값으로 캐스팅 해서 반환.

		return null;
	}

	public void nullSafeSet(PreparedStatement statement, Object value, int index)
			throws HibernateException, SQLException {
		
		// SQL을 DB에 보내기 전에 statement의 특정 위치에 들어갈 값을 변경한다.

	}

	public Object replace(Object original, Object target, Object owner)
			throws HibernateException {
		return original;
	}

	public Class returnedClass() {
		return MonetaryAmount.class;
	}

	public int[] sqlTypes() {
		return new int[] { Hibernate.BIG_DECIMAL.sqlType() };
	}

}
  • sqlTypes() 메소드는 하이버네이트가 어떤 SQL 컬럼 타입으로 DDL 스키마를 생성할 지 알려준다.
  • returnClass() 메소드는 어떤 자바 타입을 맵핑할 것인지 알려준다.
  • deepCopy()는 스냅샷 객체을 전달해 준다. 따라서, immutable한 타입일 경우에는 그냥 넘기면 된다.
  • disassemble()은 MonetaryAmount를 하이버네이트 2차 캐쉬에 집어 넣을 때 호출된다. 이곳에서 직렬화된 상태로 데이터를 캐슁한다.
  • assemble()은 캐쉬된 상태의 데이터를 MonetaryAmount 객체로 변환한다.
  • replace()는 detached 상태의 객체를 merging할 때 사용한다.
  • equals()는 dirty checking 할 때 사용한다.
  • nullSafeGet()은 ResultSet에서 데이터를 가져올 때 사용한다.
  • nullSafeSet()은 PreparedStatement에 저장할 값을 설정할 때 사용한다.

맵핑하기

@org.hibernate.annotations.Type(
    type = " persistence.MonetaryAmountUserType"
)
@Column(name = "INITIAL_PRICE")
private MonetaryAmount initialPrice;

단점

  • 하이버네이트는 Monetary Amount의 속성을 모른다. 따라서 그 안에 있는 amount나 currency를 가져오는 쿼리를 작성할 수 없다.

해결책

  • CompositeUserType을 사용하면 된다.

'Hibernate > Chapter 5' 카테고리의 다른 글

Hibernate Core VS JPA  (0) 2008.02.04
Enum Type 맵핑하기 - 실습  (0) 2008.02.04
Enum Type 만들기  (0) 2008.02.04
ParameterizedType 만들기  (0) 2008.02.04
CompositeUserType 만들기  (0) 2008.02.04
UserType만들기  (0) 2008.02.04
맵핑 타입 사용하기  (0) 2008.02.04
내장된 맵핑 타입  (0) 2008.02.04
Entity와 Value type 복습  (0) 2008.02.04
상속 맵핑 전략 선택하기  (0) 2008.02.01
상속 맵핑 전략 혼용하기  (0) 2008.02.01
top

Write a comment.