Hazırda Bekletme - Toplu İşleme
Hazırda Beklet'i kullanarak veritabanınıza çok sayıda kayıt yüklemeniz gereken bir durumu düşünün. Hibernate kullanarak bunu başarmak için kod parçacığı aşağıdadır -
Session session = SessionFactory.openSession();
Transaction tx = session.beginTransaction();
for ( int i=0; i<100000; i++ ) {
Employee employee = new Employee(.....);
session.save(employee);
}
tx.commit();
session.close();
Varsayılan olarak, Hazırda Bekletme, oturum düzeyinde önbellekteki tüm kalıcı nesneleri önbelleğe alır ve sonuçta uygulamanız bir OutOfMemoryException50.000'inci sıra civarında bir yerde. Kullanıyorsanız bu sorunu çözebilirsiniz.batch processing Hazırda bekletme ile.
Toplu işleme özelliğini kullanmak için önce hibernate.jdbc.batch_sizeparti boyutu olarak, nesne boyutuna bağlı olarak 20 veya 50 olan bir sayıya. Bu, hazırda bekletme kabına her X satırının toplu olarak ekleneceğini söyleyecektir. Bunu kodunuza uygulamak için, aşağıdaki gibi küçük değişiklikler yapmamız gerekir -
Session session = SessionFactory.openSession();
Transaction tx = session.beginTransaction();
for ( int i=0; i<100000; i++ ) {
Employee employee = new Employee(.....);
session.save(employee);
if( i % 50 == 0 ) { // Same as the JDBC batch size
//flush a batch of inserts and release memory:
session.flush();
session.clear();
}
}
tx.commit();
session.close();
Yukarıdaki kod INSERT işlemi için iyi çalışacaktır, ancak UPDATE işlemini yapmak istiyorsanız, aşağıdaki kodu kullanarak gerçekleştirebilirsiniz -
Session session = sessionFactory.openSession();
Transaction tx = session.beginTransaction();
ScrollableResults employeeCursor = session.createQuery("FROM EMPLOYEE").scroll();
int count = 0;
while ( employeeCursor.next() ) {
Employee employee = (Employee) employeeCursor.get(0);
employee.updateEmployee();
seession.update(employee);
if ( ++count % 50 == 0 ) {
session.flush();
session.clear();
}
}
tx.commit();
session.close();
Toplu İşleme Örneği
Eklemek için yapılandırma dosyasını değiştirelim hibernate.jdbc.batch_size özellik -
<?xml version = "1.0" encoding = "utf-8"?>
<!DOCTYPE hibernate-configuration SYSTEM
"http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name = "hibernate.dialect">
org.hibernate.dialect.MySQLDialect
</property>
<property name = "hibernate.connection.driver_class">
com.mysql.jdbc.Driver
</property>
<!-- Assume students is the database name -->
<property name = "hibernate.connection.url">
jdbc:mysql://localhost/test
</property>
<property name = "hibernate.connection.username">
root
</property>
<property name = "hibernate.connection.password">
root123
</property>
<property name = "hibernate.jdbc.batch_size">
50
</property>
<!-- List of XML mapping files -->
<mapping resource = "Employee.hbm.xml"/>
</session-factory>
</hibernate-configuration>
Aşağıdaki POJO Employee sınıfını düşünün -
public class Employee {
private int id;
private String firstName;
private String lastName;
private int salary;
public Employee() {}
public Employee(String fname, String lname, int salary) {
this.firstName = fname;
this.lastName = lname;
this.salary = salary;
}
public int getId() {
return id;
}
public void setId( int id ) {
this.id = id;
}
public String getFirstName() {
return firstName;
}
public void setFirstName( String first_name ) {
this.firstName = first_name;
}
public String getLastName() {
return lastName;
}
public void setLastName( String last_name ) {
this.lastName = last_name;
}
public int getSalary() {
return salary;
}
public void setSalary( int salary ) {
this.salary = salary;
}
}
Employee nesnelerini saklamak için aşağıdaki EMPLOYEE tablosunu oluşturalım -
create table EMPLOYEE (
id INT NOT NULL auto_increment,
first_name VARCHAR(20) default NULL,
last_name VARCHAR(20) default NULL,
salary INT default NULL,
PRIMARY KEY (id)
);
Aşağıda, Çalışan nesnelerini EMPLOYEE tablosu ile eşlemek için eşleme dosyası olacaktır -
<?xml version = "1.0" encoding = "utf-8"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<class name = "Employee" table = "EMPLOYEE">
<meta attribute = "class-description">
This class contains the employee detail.
</meta>
<id name = "id" type = "int" column = "id">
<generator class="native"/>
</id>
<property name = "firstName" column = "first_name" type = "string"/>
<property name = "lastName" column = "last_name" type = "string"/>
<property name = "salary" column = "salary" type = "int"/>
</class>
</hibernate-mapping>
Son olarak, kullanacağımız uygulamayı çalıştırmak için main () yöntemi ile uygulama sınıfımızı oluşturacağız. flush() ve clear() Session nesnesiyle kullanılabilen yöntemler, böylece Hibernate bu kayıtları bellekte önbelleğe almak yerine veritabanına yazmaya devam eder.
import java.util.*;
import org.hibernate.HibernateException;
import org.hibernate.Session;
import org.hibernate.Transaction;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
public class ManageEmployee {
private static SessionFactory factory;
public static void main(String[] args) {
try {
factory = new Configuration().configure().buildSessionFactory();
} catch (Throwable ex) {
System.err.println("Failed to create sessionFactory object." + ex);
throw new ExceptionInInitializerError(ex);
}
ManageEmployee ME = new ManageEmployee();
/* Add employee records in batches */
ME.addEmployees( );
}
/* Method to create employee records in batches */
public void addEmployees( ){
Session session = factory.openSession();
Transaction tx = null;
Integer employeeID = null;
try {
tx = session.beginTransaction();
for ( int i=0; i<100000; i++ ) {
String fname = "First Name " + i;
String lname = "Last Name " + i;
Integer salary = i;
Employee employee = new Employee(fname, lname, salary);
session.save(employee);
if( i % 50 == 0 ) {
session.flush();
session.clear();
}
}
tx.commit();
} catch (HibernateException e) {
if (tx!=null) tx.rollback();
e.printStackTrace();
} finally {
session.close();
}
return ;
}
}
Derleme ve Yürütme
İşte yukarıda belirtilen uygulamayı derlemek ve çalıştırmak için adımlar. Derleme ve yürütme için ilerlemeden önce PATH ve CLASSPATH'ı uygun şekilde ayarladığınızdan emin olun.
Hibernate.cfg.xml yapılandırma dosyasını yukarıda açıklandığı gibi oluşturun.
Employee.hbm.xml eşleme dosyasını yukarıda gösterildiği gibi oluşturun.
Employee.java kaynak dosyasını yukarıda gösterildiği gibi oluşturun ve derleyin.
ManageEmployee.java kaynak dosyasını yukarıda gösterildiği gibi oluşturun ve derleyin.
EMPLOYEE tablosunda 100000 kayıt oluşturacak programı çalıştırmak için ManageEmployee ikili dosyasını çalıştırın.