我有我們的軟件這個奇怪的問題。 是是生產了5年,我們有沒有這樣的問題...查詢掛起oracle 10g
問題:
我們有一個彈簧工作(調度器),它通過Hibernate會查詢,檢索對象,並修改它們。
嗯,這工作了幾年,但一個月前,查詢每天掛起5-10次(查詢每10分鐘調用一次)。當它掛起時,我們必須重新啓動服務。
下面的代碼將查詢:
@SuppressWarnings("unchecked")
public List<Delivery> findScheduledForDelivery(final String inType, final int max, final String benefitType) {
//getHibernateTemplate().clear();
return getHibernateTemplate().executeFind(new HibernateCallback() {
public Object doInHibernate(Session session) throws SQLException {
Criteria criteria = session.createCriteria(Delivery.class);
criteria.createAlias("reward","r");
criteria.createAlias("r.customer","c");
criteria.createAlias("c.inNe","i");
criteria.createAlias("r.promotion","p");
criteria.createAlias("benefit","b");
String sqlCustAlias = StringHelper.generateAlias("c", 2);
criteria.add(Expression.disjunction()
.add(Expression.eq("inStatus", INStatus.InterfaceFailure))
.add(Expression.eq("inStatus",INStatus.Initial)));
criteria.add(Expression.le("deliverAt", new Date()));
String dateString = "2000/01/01";
DateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd");
Date startDate = new Date();
try {
startDate = dateFormat.parse(dateString);
criteria.add(Expression.ge("deliverAt", startDate));
}
catch(ParseException e) {
e.printStackTrace();
}
String sqlEqual = "decode(delivered,null,0,1) = 0";
criteria.add(Expression.sql(sqlEqual));
sqlEqual = "decode(" + sqlCustAlias + ".deleteDate,null,1,0) = 1";
criteria.add(Expression.sql(sqlEqual));
if(inType != null) {
for(INType i : INType.values())
if(i.toString().equals(inType)) {
criteria.add(Expression.eq("i.inType", i));
break;
}
}
criteria.add(Expression.eq("p.active", true));
if(benefitType != null) {
if(benefitType.equals("FREECREDIT"))
criteria.add(Expression.disjunction()
.add(Expression.eq("b.type", BenefitType.FREE_CREDIT))
.add(Expression.eq("b.type", BenefitType.FREE_CREDIT_FTAM)));
else if(benefitType.equals("NONFREECREDIT")) {
criteria.add(Expression.conjunction()
.add(Expression.ne("b.type", BenefitType.FREE_CREDIT))
.add(Expression.ne("b.type", BenefitType.OTHER))
.add(Expression.ne("b.type", BenefitType.VOUCHER)));
criteria.add(Expression.isNull("b.md3Profile"));
}
if(max != 0)
criteria.setMaxResults(max);
}
criteria.addOrder(Order.desc("p.priority"));
criteria.addOrder(Order.asc("deliverAt"));
return criteria.list(); <===== hangs here
}
});
}
數據源定義,因爲這(我知道這是不應該出現在生產,但是這是它的工作的唯一辦法 - 我試圖使用Oracle連接池但隨後的查詢更常掛..):使用
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource" destroy-method="close">
<property name="driverClassName" value="${jdbc.driverClassName}" />
<property name="url" value="${jdbc.url}" />
<property name="username" value="${jdbc.username}" />
<property name="password" value="${jdbc.password}" />
<property name="connectionProperties">
<props>
<prop key="tcp.nodelay">yes</prop>
<prop key="delayRowPrefetch">20</prop>
<prop key="defaultBatchSize">5</prop>
</props>
</property>
</bean>
</beans>
軟件:
- 春天1.2.7
- 冬眠3.0.5
- 的Oracle 10.2.0.1(RAC)
- 的Oracle JDBC 10.1.0.2
- 紅帽3 EL
- 的Java 1.5_06
我一直如此遠:
- 使用oracle連接池作爲數據 源 - >掛失敗 個連接
- 使用的Oracle JDBC 10.2.0.5 - >我想我已經解決了它,而且在幾個小時後再次掛:(
有在Oracle數據庫沒有鎖,據我可以請參閱...
可能是什麼問題?
UPDATE:
在Oracle EM:
ADDM結果: SQL語句消耗顯著數據庫時被發現。 查詢消耗顯着的數據庫時間。影響81%。 用戶I/O等待97%。
- 個人SQL負責 爲顯著用戶聲明I/O等待是 發現。
- 單個數據庫段 負責重要的用戶I/O 等待被發現。
- I/O子系統 的吞吐量顯着低於預期的 。
UPDATE:(15.03.2011)
對於現在的服務工作了近48小時而掛。
我懷疑,這將解決這個問題,但我做了一些改動代碼:
刪除了decode(delivered,null,0,1) = 0
和decode(" + sqlCustAlias + ".deleteDate,null,1,0) = 1
功能查詢與和is null
語句替換它們。
交付的字段已編入索引,但索引不能用於decode
函數。
你認爲這只是巧合嗎?
UPDATE:(2011年3月16日)
的alert.log現在顯示許多條目是這樣的:
ORA-01555 caused by SQL statement below (SQL ID: affkpm4j7azc4, Query Duration=232624 sec, SCN: 0x0003.dca70559):
Tue Mar 15 17:43:06 2011
select * from (select this_.id as id5_, this_.deliverAt as deliverAt68_5_, this_.delivered as delivered68_5_, this_.inDelivery as inDelivery68_5_, this_.lastDeliveryTry as lastDeli5_68_5_, this_.tries as tries68_5_, this_.sentAt as sentAt68_5_, this_.sent as sent68_5_, this_.retry as retry68_5_, this_.inStatus as inStatus68_5_, this_.errorMessage as errorMe11_68_5_, this_.inCvsDelivery as inCvsDe12_68_5_, this_.cvsDelivered as cvsDeli13_68_5_, this_.cvsLastDeliveryTry as cvsLast14_68_5_, this_.cvsTries as cvsTries68_5_, this_.collectedPoints as collect16_68_5_, this_.smsMessage as smsMessage68_5_, this_.inOldStatus as inOldSt18_68_5_, this_.replacedDate as replace19_68_5_, this_.oldMsisdn as oldMsisdn68_5_, this_.deletedDate as deleted21_68_5_, this_.addManualDate as addManu22_68_5_, this_.stornoPromiseDate as stornoP23_68_5_, this_.stornoINDate as stornoI24_68_5_, this_.activationCode as activat25_68_5_, this_.activationExpirationDate as activat26_68_5_, this_.rewardId as rewardId68_5_, this_.benefitId as b
這似乎是從會議前3天..232624秒!
+1因爲您顯然正在週末解決生產問題。我們的行業沒有加班,但至少有幾個代表:-) – corsiKa 2011-03-12 19:13:13
非常感謝。週末預留給EMCY :-) – alesko 2011-03-12 19:15:34
我的經驗是,如果某件事情正在發揮作用,但現在不行,那只是因爲某些事情發生了變化。這段代碼沒有改變,這意味着你的數據可能有。現在,我對那裏的hibernate瞭解的很多,所以我不能分析代碼來很好地發現問題,但我會考慮數據可能發生的變化。當然,你已經完成了,我已經確定......但聳聳肩,只是值得一提。 – corsiKa 2011-03-12 19:21:55