GWT SeralizationStreamFactory reader 问题

GWT SeralizationStreamFactory reader issue

我有一个用 GWT 构建的 Web 应用程序,它需要在所有客户端发送和接收序列化数据。 (我使用的是webworkers,需要在主线程和webworkers之间交换数据)

到目前为止,我正在创建序列化对象(在这个例子中,我只是发送字符串对象的 ArrayLists,但我当然真的试图发送可序列化 class 对象的数组)

似乎没有太多关于正确使用此序列化/反序列化过程的文档,当它全部发生在客户端时。

但我的 writer 函数具有以下一般形状:

    public String streamResult(){
        SerializationStreamFactory factory = GWT.create(streamFactory.class);
        SerializationStreamWriter writer = factory.createStreamWriter();
        ArrayList<String> strlst = new ArrayList<>();
        strlst.add("First String");
        strlst.add("Second String");
        try {
           writer.writeObject(strlst);
        }  catch (Exception e) {
           printf("exception caught while serializing object");
        }
        return  writer.toString();
     }

这正确地创建了一个表示 ArrayList 数据的字符串对象

"7|0|6||788C596190777F280A9EF3D57029FB2C|java.util.ArrayList/4159755760|java.lang.String/2004016611|First String|Second String|1|2|3|2|4|5|4|6|"

但是当我对结果集进行反序列化时,我收到一个错误,该错误与尝试读取结果字符串中的整数有关。

 public void unStreamResult(String str){
        SerializationStreamFactory factory = GWT.create(streamFactory.class);
        try {
            SerializationStreamReader reader = factory.createStreamReader(str);
            stringArray.addAll((ArrayList<String>) reader.readObject());
        }  catch (Exception e){
            printf("exception caught while deseralizing object");
        }
    }

为我的 SeralizationStreamFactory 创建的 streamFactory class 定义为:

@RemoteServiceRelativePath("streamFactory")
public interface streamFactory extends RemoteService {
    ArrayList getMessage(ArrayList message);
    String getMessage(String message);
}

但是在反序列化过程中,我在某种字符串“”上得到了 NumberFormatException

Error: java.lang.NumberFormatException: For input string: "" at NumberFormatException_0.createError (Insights-0.js:13972) at NumberFormatException_0.initializeBackingError (Insights-0.js:13995) at NumberFormatException_0.Throwable_0 (Insights-0.js:13948) at NumberFormatException_0.Exception_0 (Insights-0.js:14012) at NumberFormatException_0.RuntimeException_0 (Insights-0.js:14022) at NumberFormatException_0.IllegalArgumentException_0 (Insights-0.js:46625) at new NumberFormatException_0 (Insights-0.js:46861) at __parseAndValidateInt (Insights-0.js:22987) at $prepareToRead (Insights-0.js:39707) at $unStreamResult (Insights-0.js:9415) at onMessageImpl (Insights-0.js:46204) at Worker.this$static.onmessage (Insights-0.js:46198)

现有的 GWT-RPC 协议是不对称的 - 从客户端到服务器使用一种消息格式,从服务器到客户端使用另一种格式。在我使用 RPC 的所有工作中,我一直不明白为什么会这样,除了可能使调试稍微容易一些,因为这两种消息格式不兼容,所以您一眼就知道您在寻找什么?

在任何情况下,这就是为什么这不起作用 - 您的 unStreamResult 需要一条不同格式的消息,该消息应以 //OK//EX 开头,然后是通过 JS 数组。该数组将主要包含数字,但也会包含一个字符串数组。

在 GWT-RPC 存储库的更新草案中,目前在 https://github.com/vertispan/gwt-rpc(如果 link 变得陈旧,请在这个答案上留言,我会更新),我们已经更改流 readers 和 writers 是完全对称的。这避免了你和其他人所面临的混淆,并使得序列化格式可以独立使用,例如与 Web Worker 通信,或者对 Blob 进行一些简单的序列化以用于 IndexedDb 或其他东西(需要注意的是此格式 版本化,因此在您的应用程序更新过程中保留的数据可能不再有效。

如果在我完成那个项目之前你必须让这个格式工作,看看像 https://github.com/niloc132/webbit-gwt/blob/master/workers/src/main/java/com/colinalworth/gwt/worker/client/impl/StreamReader.java 的东西(和 StreamWriter.java 在同一个包中) - 这些只是 [=13 的子类型=] 和 AbstractSerializationStreamWriter,但仔细编写以避免客户端和 reader 之间的任何差异。这些是为使用 ByteBuffers 而编写的(它们本身包装了 JS TypedArrays 以获得更好的性能)。在 gwt-rpc 项目中有一个 "modernized" 版本,用于字符串和 ByteBuffers,但它们可能与旧的 RPC 不完全兼容。使用这些也带来了额外的工作:您必须停止使用 factory.createStreamWriter() 等来为您构建 reader 和 writer,然后您必须从 RemoteServiceProxy sub[] 中访问 serializer 字段=37=](也许是 JSNI?)。


但是对于您的 WebSockets 用例,您实际上不需要完全对称的线路格式 - 您只需要通过线路将有效负载发送到服务器并让它对其进行解码,然后制作自己的回复,并发回给客户。一旦在客户端上,您的 unStreamResult 消息将正确读取该响应负载。

虽然我从不劝阻某人重新发明轮子,但也可以考虑使用我之前 link 编写的 gwt websocket 项目,因为它已经解决了其中的许多问题。它当然并不完美,但随着我们将其作为更新后的 GWT-RPC 模块中的第一个 class 功能,它会越来越接近。