gwt - 在RPC调用中使用List <serializable>?</serializable>

时间:2010-06-17 07:49:40

标签: java gwt serialization rpc gwt-rpc

我有一个RPC服务,使用以下方法:

public List<Serializable> myMethod(TransactionCall call) {...}

但是当分析此方法时,我收到警告,然后rpc调用失败

Analyzing 'my.project.package.myService' for serializable types
Analyzing methods:
public abstract java.util.List<java.io.Serializable> myMethod(my.project.package.TransactionCall call)
Return type: java.util.List<java.io.Serializable>
[...]
java.io.Serializable
Verifying instantiability
(!) Checking all subtypes of Object wich qualify for serialization

似乎我不能将Serializable用于我的List ...我可以使用我自己的界面(类似于AsyncDataInterface,它实现了Serializable接口)但事实是我的方法将返回一个列表自定义对象和基本对象(例如Strings,int ....)。

所以我的问题是:

  • 这是一种标准行为吗? (我无法弄清楚为什么我不能在这种情况下使用这个界面)
  • 有没有人为这种情况找到解决方法?

3 个答案:

答案 0 :(得分:29)

在RPC调用中传递对象时,最好在RPC接口中声明具体的参数类型。如果由于某种原因您无法在RPC接口中使用具体类,请尝试尽可能具体。

这是因为GWT编译器在发出javascript时必须考虑编译单元中List的所有可能变体。这包括在类路径中扩展List和Serializable接口的所有类。排列可能很大,这将影响您的编译时间以及应用程序下载大小。

所以最好的方法是将界面定义为

public ArrayList<YourType> myMethod(TransactionCall call) {...}

而不是

public List<Serializable> myMethod(TransactionCall call) {...}

这样编译器只需为ArrayList和YourType扩展生成编译单元。好处是编译时间更短,编译的javascript文件更小,因此可以更快地下载应用程序。

如果必须在RPC调用中返回各种不相关的对象,请尝试创建包装类并返回包装类的包装返回值的对象。使用RPC方法定义中的包装类。抵制将包装字段声明为Object或Serializable的冲动,您将否定使用包​​装器获得的所有序列化优势。相反,您可以为希望通过RPC调用返回的每个具体类型定义一个Wrapper接口和一小组Wrapper实现。

答案 1 :(得分:1)

您可能希望检查序列化策略文件不是问题的根源。

Quote from GWT documentation

  

但是,有一个条件可以在新的GWT RPC系统中启用对java.io.Serializable的支持。

     

RPC现在在GWT编译期间生成序列化策略文件。序列化策略文件包含可以序列化的允许类型的白名单。它的名称是一个强大的哈希名称,后跟.gwt.rpc。为了启用对java.io.Serializable的支持,应用程序将通过网络发送的类型必须包含在序列化策略白名单中。此外,序列化策略文件必须作为公共资源部署到Web服务器,可通过ServletContext.getResource()从RemoteServiceServlet访问。如果未正确部署,RPC将以1.3.3兼容模式运行,并拒绝序列化实现java.io.Serializable的类型。

答案 2 :(得分:0)

我没有看到定义List&lt; Serializable&gt;的重点。作为返回值。 Serializable类型在服务API声明中不提供其他信息。 GWT无论如何都会在运行时进行序列化检查。

在你的情况下,如果列表元素没有Object之外没有共同的祖先,我会使用List&lt;?&gt ;.