我正在开发一个关于gae / j的应用程序。
我有一个实体设置,我试图坚持列表的字段。问题是我得到了ClassCastException。
@Entity
public class Party {
@Id
@GeneratedValue (strategy = GenerationType.IDENTITY)
public Key Id;
@ElementCollection(fetch = FetchType.EAGER)
public List<Long> guests;
public List<Long> getGuests(){
if(guests== null){
guests = new ArrayList<Long>();
}
return guests;
}
public void setGuests(List<Long> guests){
this.guests = guests;
}
}
当我测试代码时,我在堆栈跟踪中收到此错误。
com.google.api.server.spi.SystemService invokeServiceMethod: java.lang.Long cannot be cast to java.util.List
java.lang.ClassCastException: java.lang.Long cannot be cast to java.util.List
at com.google.appengine.datanucleus.TypeConversionUtils.datastoreValueToPojoCollection(TypeConversionUtils.java:456)
at com.google.appengine.datanucleus.TypeConversionUtils.datastoreValueToPojoValue(TypeConversionUtils.java:377)
at com.google.appengine.datanucleus.FetchFieldManager.fetchFieldFromEntity(FetchFieldManager.java:463)
at com.google.appengine.datanucleus.FetchFieldManager.fetchObjectField(FetchFieldManager.java:408)
at org.datanucleus.state.AbstractStateManager.replacingObjectField(AbstractStateManager.java:2353)
at com.mastermindcode.theincrowd.Party.jdoReplaceField(Party.java)
at com.mastermindcode.theincrowd.Party.jdoReplaceFields(Party.java)
at org.datanucleus.state.JDOStateManager.replaceFields(JDOStateManager.java:1935)
at org.datanucleus.state.JDOStateManager.replaceFields(JDOStateManager.java:1962)
at com.google.appengine.datanucleus.DatastorePersistenceHandler.fetchObject(DatastorePersistenceHandler.java:567)
at org.datanucleus.state.JDOStateManager.loadFieldsFromDatastore(JDOStateManager.java:1638)
at org.datanucleus.state.JDOStateManager.loadUnloadedFieldsInFetchPlan(JDOStateManager.java:1363)
at org.datanucleus.state.JDOStateManager.detach(JDOStateManager.java:2718)
at org.datanucleus.ObjectManagerImpl.performDetachOnCloseWork(ObjectManagerImpl.java:4571)
at org.datanucleus.ObjectManagerImpl.performDetachOnClose(ObjectManagerImpl.java:4534)
at org.datanucleus.ObjectManagerImpl.close(ObjectManagerImpl.java:1105)
at org.datanucleus.api.jpa.JPAEntityManager.close(JPAEntityManager.java:193)
at com.mastermindcode.theincrowd.PartyEndpoint.listParty(PartyEndpoint.java:104)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:45)
at com.google.api.server.spi.SystemService.invokeServiceMethod(SystemService.java:359)
at com.google.api.server.spi.SystemServiceServlet.execute(SystemServiceServlet.java:124)
at com.google.api.server.spi.SystemServiceServlet.doPost(SystemServiceServlet.java:82)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:637)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
at org.mortbay.jetty.servlet.ServletHolder.handle(ServletHolder.java:511)
at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1166)
at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
at org.mortbay.jetty.servlet.ServletHandler.handle(ServletHandler.java:388)
at org.mortbay.jetty.security.SecurityHandler.handle(SecurityHandler.java:216)
at org.mortbay.jetty.servlet.SessionHandler.handle(SessionHandler.java:182)
at org.mortbay.jetty.handler.ContextHandler.handle(ContextHandler.java:765)
at org.mortbay.jetty.webapp.WebAppContext.handle(WebAppContext.java:418)
at org.mortbay.jetty.handler.HandlerWrapper.handle(HandlerWrapper.java:152)
at org.mortbay.jetty.Server.handle(Server.java:326)
at org.mortbay.jetty.HttpConnection.handleRequest(HttpConnection.java:542)
at org.mortbay.jetty.HttpConnection$RequestHandler.headerComplete(HttpConnection.java:923)
at org.mortbay.jetty.HttpConnection.handle(HttpConnection.java:404)
at com.google.tracing.TraceContext$TraceContextRunnable.runInContext(TraceContext.java:437)
at com.google.tracing.TraceContext$TraceContextRunnable$1.run(TraceContext.java:444)
at com.google.tracing.CurrentContext.runInContext(CurrentContext.java:188)
at com.google.tracing.TraceContext$AbstractTraceContextCallback.runInInheritedContextNoUnref(TraceContext.java:308)
at com.google.tracing.TraceContext$AbstractTraceContextCallback.runInInheritedContext(TraceContext.java:300)
at com.google.tracing.TraceContext$TraceContextRunnable.run(TraceContext.java:441)
at java.lang.Thread.run(Thread.java:724)
我很抱歉,如果有一个我忽略的简单答案,但我想要做的就是在聚会对象的列表字段中存储用户ID列表(类型为Long)。我已经尝试了每个jpa注释并阅读了应用程序引擎文档几天寻找解决方案。
我通常可以找到我的bug查看堆栈跟踪,但是这个没有告诉我代码中的bug在哪里。如果您在第104行注意到Partyendpoint.java中导致的问题,那么它就是实体管理器关闭的地方。
感谢您的帮助......
更新:我添加了我正在调用的导致问题的方法。我正在使用云端点向android和ios设备发送集合响应。
@SuppressWarnings({ "unchecked", "unused" })
@ApiMethod(name = "listParty")
public CollectionResponse<Party> listParty(@Nullable @Named("cursor") String cursorString,@Nullable @Named("limit") Integer limit) {
EntityManager mgr = null;
Cursor cursor = null;
List<Party> execute = null;
try {
mgr = getEntityManager();
Query query = mgr.createQuery("select from Party as Party");
if (cursorString != null && cursorString != "") {
cursor = Cursor.fromWebSafeString(cursorString);
query.setHint(JPACursorHelper.CURSOR_HINT, cursor);
}
if (limit != null) {
query.setFirstResult(0);
query.setMaxResults(limit);
}
execute = (List<Party>) query.getResultList();
cursor = JPACursorHelper.getCursor(execute);
if (cursor != null)
cursorString = cursor.toWebSafeString();
// Tight loop for fetching all entities from datastore and accomodate
// for lazy fetch.
for (Party obj : execute)
;
} finally {
mgr.close();
}
return CollectionResponse.<Party> builder().setItems(execute)
.setNextPageToken(cursorString).build();
}
答案 0 :(得分:2)
您可能正在从代码中进行计数查询并将结果转换为L ist<>
,因此您将面临错误。
以下是使用EntityManager
获取计数值的方法(您也可以使用Session
)。
Long count = (Long)em.createQuery("SELECT COUNT(d) FROM Test d").getSingleResult();
或
Long count = em.createQuery("SELECT COUNT(d) FROM Test d", Long.class).getSingleResult();