天天看點

Google App Engine平台下JDOQL查詢報異常的問題解決方案

 在java應用程式開發中使用JDO資料存儲的方式,裡面涉及到以對象為基礎建立永久性資料。看不到資料庫檔案也看不到表,隻有自定義的實體類,存儲的方式也很簡單,定義一個實體類,然後将其屬性指派,然後調用PersistenceManager 類提供的方法存儲這個對象即可。但是在資料的查詢過程中卻是傷透腦筋。以下是我近幾天遇到的問題和自己琢磨的解決方案,其中Baby是我定義的實體類。

1.執行GetObjectById()抛出異常” Could not retrieve entity of kind Baby with key Baby("31~60")”其中Baby是我定義的實體類,30~61是我傳遞的一個作為Id的參數。一直以為哪裡的代碼出現問題了或者參數的格式不對等問題,經反複試驗才知道。這就是GetObjectById()這個方法本身的問題。不像SQL中傳入個Id查詢有則傳回這個對象,沒有則傳回空,JDO中的資料查詢是傳入的Id必須能查到資料,若沒有就抛出上述異常。

解決方案:将GetObjectById()方法用try/catch括起來,形如:

try 

   Baby baby=PM.GetObjectById(“30~61”); 

   return baby; 

Catch(Exception e) 

   return null; 

這樣,有這個資料傳回該記錄沒有則傳回null

2.執行newQuery()抛出類型轉換錯誤

具體英文我忘了,意思就是說意思就是說無法将Baby集合轉換成Baby類型,也就是List<Baby>無法轉換成Baby類型。在SQL中可能根據一條查詢語句”select * from Baby where Id=’31~60’”調用方法傳回的可以轉換成Baby對象,可是JDO中調用newQuery()不管傳入的查詢語句參數是什麼,都會傳回一個List<Object>類型。

解決方案:調用newQuery()就将其結果指派一個List<Object>的變量吧。

3. 執行newQuery()方法抛出” Object Manager has been closed”的異常

這是位于DataServer類中的查詢方法代碼:

public static List<Baby> GetBabyInfoList(String queryString)  

   PersistenceManager pm = PMF.get().getPersistenceManager(); 

   Query query = pm.newQuery(queryString); 

   @SuppressWarnings("unchecked") 

   List<Baby> babys = (List<Baby>) query.execute(); 

   pm.close(); 

   return babys; 

我在另一處調用

String queryStr=”select from Baby”; 

List<Baby> babies=DataServer.GetBabyInfoList(queryStr); 

結果一運作就抛那個異常了。原因就是GetBabyInfoList方法中的pm.close();,将這句去掉就OK了,了解JDO的人士可能會說将實體類定義成可分離的再在代碼中加句pm.setDetachAllOnCommit(true);。事實無情的告訴你,不行!

解決方案:去掉方法中在傳回對象前的pm.close();語句。

本文轉自HDDevTeam 51CTO部落格,原文連結:http://blog.51cto.com/hddev/651975,如需轉載請自行聯系原作者