OpenJpa 批量插入
OpenJpa batch insert
我已经读过 and that 但它不适合我。
我有 openjpa 实现,我需要进行批量插入。
我有一些实体和 Spring 我从 EntityManagerFactory 注入我的事务管理器和 EntityManager 就像
<tx:annotation-driven transaction-manager="transactionManager"/>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory"/>
</bean>
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource"/>
<property name="persistenceUnitName" value="JpaPersistenceUnit"/>
<property name="jpaPropertyMap">
<map>
<entry key="openjpa.jdbc.DBDictionary" value="org.apache.openjpa.jdbc.sql.OracleDictionary" />
<entry key="openjpa.ConnectionFactoryProperties" value="PrintParameters=true" />
</map>
</property>
</bean>
在class我有
@PersistenceContext
protected EntityManager em;
AtomicInteger size = new AtomicInteger();
@TransactionalRollback
public void saveLogs(Logs log) {
int i = size.incrementAndGet();
int batchSize=100;
em.persist(log);
if(i%batchSize==0){
em.flush();
em.clear();
}
}
在这里,我不知道该怎么办。因为,如果我使用 flush() 我会出错,我无法使用 Shared EntityManager 做任何事情。当我只坚持时,还可以,但是每个数据都会立即提交。
也许可以使用 SpringBuilder 和一些 nativeQuery 进行批量插入?
喜欢
String insert = "INSERT into SIEBEL_METHOD_LOGS (?1,?2,?3,?4) VALUES ";
StringBuilder builder = new StringBuilder(insert);
builder.append(
"(" + log.getMethod() + "), "
+ "(" + log.getClient() + "), "
+ "(" + log.getStartDate() + "), "
+ "(" + log.getResponseTime() + "), "
+ "(" + log.getIsError() + ")");
Query query = em.createNativeQuery(builder.toString());
query.executeUpdate();
但是,我不确定。
P.S。另外,我不明白那是什么意思
org.apache.openjpa.jdbc.sql.OracleDictionary 有字段
// batch limit
private int defaultBatchLimit = 100;
什么时候生效?因为每当我坚持并结束我的方法时,我都会刷新到数据库中,并且它不依赖于我坚持到数据库中的 100 或 5 个元素。他们会在那里。
我使用了那个解决方案,但也许它可能更优雅
public class LoggerClass {
private static final int batchSize = 100;
private List<MethodsLog> logsList;
private AtomicLong sizeList;
private void initList() {
this.logsList = new ArrayList<>(batchSize);
this.sizeList = new AtomicLong();
}
public void saveLogs(MethodsLog log) {
long i = sizeList.incrementAndGet();
logsList.add(log.toJpa());
if (i % batchSize == 0) {
saveToDBAndClear(logsList);
initList();
}
}
private synchronized void saveToDBAndClear(List<MethodsLog> logs) {
MethodsService.saveLogs(logs);
}
@TransactionalRollback
public void saveLogs(List<MethodLogs> logs) {
for (MethodLogs log : logs) {
em.persist(log);
}
}
}
我已经读过
<tx:annotation-driven transaction-manager="transactionManager"/>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory"/>
</bean>
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource"/>
<property name="persistenceUnitName" value="JpaPersistenceUnit"/>
<property name="jpaPropertyMap">
<map>
<entry key="openjpa.jdbc.DBDictionary" value="org.apache.openjpa.jdbc.sql.OracleDictionary" />
<entry key="openjpa.ConnectionFactoryProperties" value="PrintParameters=true" />
</map>
</property>
</bean>
在class我有
@PersistenceContext
protected EntityManager em;
AtomicInteger size = new AtomicInteger();
@TransactionalRollback
public void saveLogs(Logs log) {
int i = size.incrementAndGet();
int batchSize=100;
em.persist(log);
if(i%batchSize==0){
em.flush();
em.clear();
}
}
在这里,我不知道该怎么办。因为,如果我使用 flush() 我会出错,我无法使用 Shared EntityManager 做任何事情。当我只坚持时,还可以,但是每个数据都会立即提交。
也许可以使用 SpringBuilder 和一些 nativeQuery 进行批量插入? 喜欢
String insert = "INSERT into SIEBEL_METHOD_LOGS (?1,?2,?3,?4) VALUES ";
StringBuilder builder = new StringBuilder(insert);
builder.append(
"(" + log.getMethod() + "), "
+ "(" + log.getClient() + "), "
+ "(" + log.getStartDate() + "), "
+ "(" + log.getResponseTime() + "), "
+ "(" + log.getIsError() + ")");
Query query = em.createNativeQuery(builder.toString());
query.executeUpdate();
但是,我不确定。
P.S。另外,我不明白那是什么意思 org.apache.openjpa.jdbc.sql.OracleDictionary 有字段
// batch limit
private int defaultBatchLimit = 100;
什么时候生效?因为每当我坚持并结束我的方法时,我都会刷新到数据库中,并且它不依赖于我坚持到数据库中的 100 或 5 个元素。他们会在那里。
我使用了那个解决方案,但也许它可能更优雅
public class LoggerClass {
private static final int batchSize = 100;
private List<MethodsLog> logsList;
private AtomicLong sizeList;
private void initList() {
this.logsList = new ArrayList<>(batchSize);
this.sizeList = new AtomicLong();
}
public void saveLogs(MethodsLog log) {
long i = sizeList.incrementAndGet();
logsList.add(log.toJpa());
if (i % batchSize == 0) {
saveToDBAndClear(logsList);
initList();
}
}
private synchronized void saveToDBAndClear(List<MethodsLog> logs) {
MethodsService.saveLogs(logs);
}
@TransactionalRollback
public void saveLogs(List<MethodLogs> logs) {
for (MethodLogs log : logs) {
em.persist(log);
}
}
}