簡體   English   中英

gwt 序列化策略托管模式不同步

[英]gwt serialization policy hosted mode out of sync

在托管模式下運行我的 GWT 應用程序(gwt 2.0.4)時,調用遠程 Tomcat 上運行的 RPC 方法,我得到 GWT 序列化異常:

INFO: GwtRpcEventSrvc: ERROR: The serialization policy file '/84EC7BA65AF8175BAA99B47877FDE163.gwt.rpc' was not found; did you forget to include it in this deployment?

SEVERE: GwtRpcEventSrvc: WARNING: Failed to get the SerializationPolicy '84EC7BA65AF8175BAA99B47877FDE163' for module 'http://host:19980/MYAPP/'; a legacy, 1.3.3 compatible, serialization policy will be used.  Youmay experience SerializationExceptions as a result.

SEVERE: Exception while dispatching incoming RPC call
Throwable occurred: com.google.gwt.user.client.rpc.SerializationException: java.lang.reflect.InvocationTargetException
.at com.google.gwt.user.server.rpc.impl.ServerSerializationStreamWriter.serializeWithCustomSerializer(ServerSerializationStreamWriter.java:760)
.at com.google.gwt.user.server.rpc.impl.ServerSerializationStreamWriter.serializeImpl(ServerSerializationStreamWriter.java:723)
.at com.google.gwt.user.server.rpc.impl.ServerSerializationStreamWriter.serialize(ServerSerializationStreamWriter.java:612)
.at com.google.gwt.user.client.rpc.impl.AbstractSerializationStreamWriter.writeObject(AbstractSerializationStreamWriter.java:129)
.at com.google.gwt.user.server.rpc.impl.ServerSerializationStreamWriter$ValueWriter$8.write(ServerSerializationStreamWriter.java:152)
...
Caused by: com.google.gwt.user.client.rpc.SerializationException: Type 'com.mypackage.data.MyData' was not assignable to 'com.google.gwt.user.client.rpc.IsSerializable' and did not have a custom field serializer.For security purposes, this type will not be serialized.: instance = com.mypackage.data.MyData@1b061b06
.at com.google.gwt.user.server.rpc.impl.ServerSerializationStreamWriter.serialize(ServerSerializationStreamWriter.java:610)
.at com.google.gwt.user.client.rpc.impl.AbstractSerializationStreamWriter.writeObject(AbstractSerializationStreamWriter.java:129)
.at com.google.gwt.user.client.rpc.core.java.util.Collection_CustomFieldSerializerBase.serialize(Collection_CustomFieldSerializerBase.java:43)
.at com.google.gwt.user.client.rpc.core.java.util.LinkedList_CustomFieldSerializer.serialize(LinkedList_CustomFieldSerializer.java:36)
.... 33 more

托管模式生成序列化策略文件 (*.gwt.rpc),其 md5 與在 GWT 編譯期間創建的那些文件不同——這些文件部署在我的服務器上。 GWT 缺少托管模式客戶端所需的序列化策略文件。

在非托管模式下運行時,一切都很好。

我嘗試通過 Ant 或 Eclipse 調試配置啟動托管模式,結果相同。 GWT 編譯類路徑和托管模式類路徑(包括)相同。

GWT 編譯 Ant 腳本:

<java failonerror="true" fork="true" classname="com.google.gwt.dev.Compiler">
  <classpath>
    <pathelement location="${basedir}/src" />
    <pathelement location="${dir.build.root}/ProjectA/src" />
    <pathelement location="${dir.build.root}/ProjectB/src" />
    <pathelement location="${dir.build.root}/ProjectC/src" />
    <pathelement location="${dir.build.root}/ProjectD/src" />
    <pathelement location="${dir.build.root}/ProjectE/src" />
    <pathelement location="${dir.root}/ProjectD/src" />
    <pathelement location="${dir.root}/THIRDPARTY/build/athirdparty.jar" />
    <pathelement location="${dir.commons.gwtcompiler}/gwt-user.jar" />
    <pathelement location="${dir.commons.gwtcompiler}/gwt-dev.jar" />
    <pathelement location="../ExternalLibs/libs/gwt-log-3.0.0.jar" />
<!-- JAXB API sources needed for GWT compilation of JAXB annotated classes -->
    <pathelement location="../ExternalLibs/nonshipjars/jaxb-api-src.zip" />
  </classpath>
  <jvmarg value="-Xmx1g" />
  <jvmarg value="-Dgwt.nowarn.metadata" />
  <arg line="-localWorkers 2 -style OBF" />
  <arg line="-war ${basedir}/www" />
  <arg line="-extra ${basedir}/build" />
  <arg value="com.myapp.Main" />
</java>

托管模式啟動 - Ant 腳本:

<target name="hosted" description="Run hosted mode">
  <java failonerror="true" fork="true" classname="com.google.gwt.dev.HostedMode">
    <classpath>
        <pathelement location="${basedir}/src" />
        <pathelement location="${dir.build.root}/ProjectA/src" />
        <pathelement location="${dir.build.root}/ProjectB/src" />
        <pathelement location="${dir.build.root}/ProjectC/src" />
        <pathelement location="${dir.build.root}/ProjectD/src" />
        <pathelement location="${dir.build.root}/ProjectE/src" />
        <pathelement location="${dir.root}/ProjectD/src" />
        <pathelement location="${dir.root}/THIRDPARTY/build/athirdparty.jar" />
        <pathelement location="${dir.commons.gwtcompiler}/gwt-user.jar" />
        <pathelement location="${dir.commons.gwtcompiler}/gwt-dev.jar" />
        <pathelement location="../ExternalLibs/libs/gwt-log-3.0.0.jar" />
    <!-- JAXB API sources needed for GWT compilation of JAXB annotated classes -->
        <pathelement location="../ExternalLibs/nonshipjars/jaxb-api-src.zip" />
    </classpath>
    <jvmarg value="-Xmx1g" />
    <jvmarg value="-Dgwt.nowarn.metadata" />
    <arg line="com.myapp.Main" />
    <arg line="-startupUrl" />
    <arg line=" http://host:19980/MYAPP/Main.html" />
    <arg line="-whitelist" />
    <arg line="^http[:][/][/]host[:]19980" />
    <arg line="-whitelist" />
    <arg line=" ^http[:][/][/]localhost" />
    <arg line="-whitelist" />
    <arg line="^http[:][/][/]127.0.0.1" />
    <arg line="-port" />
    <arg line="8080" />
    <arg line="-noserver" />
    <arg line="-logLevel" />
    <arg line="DEBUG" />
  </java>
</target>

RPC 方法簽名:

public List<MyData> getSmpeWorkDddefZonesData(String processId);

MyData定義(在 ProjectE 中聲明為非 GWT 項目 - 數據層):

package com.mypackage.data;

import java.io.Serializable;

public interface MyData extends Serializable {...

MyData 鏈接在從另一個 GWT 模塊繼承的模塊中: com.mypackage.Data.gwt.xml :CFABB83

<module>
  <source path="data" />
</module>

主模塊com.myapp.Main.gwt.xml

...
  <inherits name="com.mypackage.Data" />
...

如何使托管生成相同的序列化策略文件?

我一直有同樣的問題。 我看到的唯一解決方案是確保兩邊都有相同的.gwt.rpc文件。

這意味着,每次啟動或重新加載開發模式時,都必須用新生成的文件替換部署在 web 服務器上的舊.gwt.rpc文件。

或者您將開發模式戰爭 output 目錄指向 web 服務器上下文。 並確保 web 服務器已打開自動部署。 因此,每次開發模式更改文件時,web 服務器會自動重新加載文件。

Based on what I see in com.google.gwt.user.rebind.rpc.ProxyCreator GWT generates the names of the serialization policy .gwt.rpc files by their content (md5).

因此,出於某種原因,超級開發模式中的序列化策略與正常構建期間生成的策略不同。

以下方法為我解決了這個問題:

  1. 打開為常規構建生成的序列化策略.gwt.rpc文件
  2. 打開為 Super Dev Mode 生成的序列化策略.gwt.rpc文件。 您可以通過查看 Super Dev Mode 啟動時打印的工作目錄來找到它的位置。 例如,在我的情況下是:“workDir: C:\Users\your_user\AppData\Local\Temp\gwt-codeserver-5658052675265790575.tmp”
  3. 比較這 2 個文件 - 這可以很好地提示您問題可能出在哪里。 在我的情況下,序列化策略中添加了 2 個不需要的類型,我可以簡單地將它們從項目中完全刪除。
  4. 修復差異后, .gwt.rpc文件名應該再次相同,問題將得到修復:)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM