hibernate의 HQL을 알아보자.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | package com.zest.hibernate.chapter10.crud; import javax.persistence.Entity; import javax.persistence.GeneratedValue; import javax.persistence.GenerationType; import javax.persistence.Id; import javax.persistence.NamedQueries; import javax.persistence.Table; @Entity @Table(name="USER_DETAILS") public class UserDetails { @Id @GeneratedValue(strategy=GenerationType.AUTO) private int userId; private String userName; public int getUserId() { return userId; } public void setUserId(int userId) { this.userId = userId; } public String getUserName() { return userName; } public void setUserName(String userName) { this.userName = userName; } } | cs |
위와 같은 테이블을 생성한다.
먼저 데이터를 insert 한다. 이 부분은 기존에 만들어 놓은 코드를 조금 수정해서 insert를 한다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 | @Test public void insertTest() { // hibernate의 persitst를 위한 클래스 AnnotationConfiguration config = new AnnotationConfiguration(); config.addAnnotatedClass(UserDetails.class); // db 접속 정보들을 저장. config.configure("hibernate.cfg.xml"); // db 접속후 여러개의 테이블을 자동으로 제너레이트 해주는 객체. // <property name="hibernate.default_schema">TESTSCHEMA</property> 이구문역시 // 마찬가지임. new SchemaExport(config).create(true, true); // 아래 두개의 구문은 객체를 트랜잭션을 컨트롤. SessionFactory factory = config.buildSessionFactory(); Session session = factory.getCurrentSession(); session.beginTransaction(); for (int i = 0; i < 10; i++) { UserDetails user = new UserDetails(); user.setUserName("user " + i); session.save(user); } session.getTransaction().commit(); // session.close(); } | cs |
user0, user1 ........... 이런 user를 총 10개를 만들었다. 그럼 기존에 사용했던 방식으로 select의 결과물을 가져와보자.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | @Test public void getTest() { // hibernate의 persitst를 위한 클래스 AnnotationConfiguration config = new AnnotationConfiguration(); config.addAnnotatedClass(UserDetails.class); // db 접속 정보들을 저장. config.configure("hibernate.cfg.xml"); // db 접속후 여러개의 테이블을 자동으로 제너레이트 해주는 객체. // <property name="hibernate.default_schema">TESTSCHEMA</property> 이구문역시 // 마찬가지임. // new SchemaExport(config).create(true, true); // 아래 두개의 구문은 객체를 트랜잭션을 컨트롤. SessionFactory factory = config.buildSessionFactory(); Session session = factory.getCurrentSession(); session.beginTransaction(); UserDetails user = (UserDetails) session.get(UserDetails.class, 6); System.out.println("name\t"+user.getUserName()); session.getTransaction().commit(); // session.close(); } | cs |
session.get이라는 함수를 통해 파라미터로 어느 테이블(객체), 기본키를 넣어서 값을 가져오는 예제이다.
그럼 hql를 해보자.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | @Test public void hsqlTest1() { // hibernate의 persitst를 위한 클래스 AnnotationConfiguration config = new AnnotationConfiguration(); config.addAnnotatedClass(UserDetails.class); // db 접속 정보들을 저장. config.configure("hibernate.cfg.xml"); // db 접속후 여러개의 테이블을 자동으로 제너레이트 해주는 객체. // <property name="hibernate.default_schema">TESTSCHEMA</property> 이구문역시 // 마찬가지임. // new SchemaExport(config).create(true, true); // 아래 두개의 구문은 객체를 트랜잭션을 컨트롤. SessionFactory factory = config.buildSessionFactory(); Session session = factory.getCurrentSession(); session.beginTransaction(); //hibernate 용으로. Query query= session.createQuery("from UserDetails"); List users = query.list(); session.getTransaction().commit(); // session.close(); System.out.println("list size==>"+users.size()); } | cs |
위의 내용은 전체 리스트를 가져오는 예제이다. 이때 중요한 메소드는 createQuery라는 메소드인데 이 뒤는 sql문과 매우 흡사하다. 여기서 중요한 점은 UserDetails는 table명이 아니라 객체 라는 점이다. jpa에서는 jpa ql 이라는 것과 거의 비슷하게 맵핑이 될것이다.
한개더 예제를 해보자.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | @Test public void hsqlWhereTest() { // hibernate의 persitst를 위한 클래스 AnnotationConfiguration config = new AnnotationConfiguration(); config.addAnnotatedClass(UserDetails.class); // db 접속 정보들을 저장. config.configure("hibernate.cfg.xml"); // db 접속후 여러개의 테이블을 자동으로 제너레이트 해주는 객체. // <property name="hibernate.default_schema">TESTSCHEMA</property> 이구문역시 // 마찬가지임. // new SchemaExport(config).create(true, true); // 아래 두개의 구문은 객체를 트랜잭션을 컨트롤. SessionFactory factory = config.buildSessionFactory(); Session session = factory.getCurrentSession(); session.beginTransaction(); //hibernate 용으로. Query query= session.createQuery("from UserDetails where userId >5"); List users = query.list(); session.getTransaction().commit(); // session.close(); System.out.println("list size==>"+users.size()); } | cs |
위의 예제는 where절이 추가 되었으며 마찬가지로 UserDetails의 멤버 변수의 값을 5보다 큰 값을 가져오는 예제이다.
이번엔 게시판 또는 그리드에서 많이 쓰는 paging에 대해 보자.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | @Test public void hsqlpageingTest2() { // hibernate의 persitst를 위한 클래스 AnnotationConfiguration config = new AnnotationConfiguration(); config.addAnnotatedClass(UserDetails.class); // db 접속 정보들을 저장. config.configure("hibernate.cfg.xml"); // db 접속후 여러개의 테이블을 자동으로 제너레이트 해주는 객체. // <property name="hibernate.default_schema">TESTSCHEMA</property> 이구문역시 // 마찬가지임. // new SchemaExport(config).create(true, true); // 아래 두개의 구문은 객체를 트랜잭션을 컨트롤. SessionFactory factory = config.buildSessionFactory(); Session session = factory.getCurrentSession(); session.beginTransaction(); //hibernate 용으로. Query query= session.createQuery("from UserDetails "); //시작 row를 설정. query.setFirstResult(5); //결과 개수 query.setMaxResults(4); List<UserDetails> users = (List<UserDetails>)query.list(); session.getTransaction().commit(); // session.close(); for(UserDetails u : users){ System.out.println(u.getUserName()); } } | cs |
setFirstResult 메소드와 setMaxResults가 추가 되었다. 이 메소드를 이용해 paging을 쉽게 구현할 것이다.
이번엔 preparedstatement와 비슷한 binding에 대해 알아보자.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 | @Test public void hsqlBindingTest2() { // hibernate의 persitst를 위한 클래스 AnnotationConfiguration config = new AnnotationConfiguration(); config.addAnnotatedClass(UserDetails.class); // db 접속 정보들을 저장. config.configure("hibernate.cfg.xml"); // db 접속후 여러개의 테이블을 자동으로 제너레이트 해주는 객체. // <property name="hibernate.default_schema">TESTSCHEMA</property> 이구문역시 // 마찬가지임. // new SchemaExport(config).create(true, true); // 아래 두개의 구문은 객체를 트랜잭션을 컨트롤. SessionFactory factory = config.buildSessionFactory(); Session session = factory.getCurrentSession(); session.beginTransaction(); String minUserId= "5"; //hibernate 용으로. Query query= session.createQuery("from UserDetails where userId > ?"); query.setInteger(0, Integer.parseInt(minUserId)); List<UserDetails> users = (List<UserDetails>)query.list(); session.getTransaction().commit(); // session.close(); for(UserDetails u : users){ System.out.println(u.getUserName()); } } | cs |
hql에 ? 라는 바인딩 변수가 있다. 이 값을 setInteger로 바인딩 하는 메소드를 추가하고 리스트를 가져오는 예제이다. preparedstatement와 매우 흡사하다.
여기까지 하이버네이트는 끝낸다.
모든 예제는 https://github.com/zest133/hibernateTest.git 에서 있다.