在 GWT-RPC 中使用嵌套枚举
Posted
技术标签:
【中文标题】在 GWT-RPC 中使用嵌套枚举【英文标题】:Using a nested enum in GWT-RPC 【发布时间】:2011-10-18 10:37:58 【问题描述】:我有一个带有嵌套枚举的枚举(我想将其设为私有),但是当我这样做时,GWT 告诉我嵌套枚举不可见并引发异常。
public enum OuterEnum
A(NestedEnum.X),
B(NestedEnum.Y),
C(NestedEnum.X);
NestedEnum nestedValue;
private OuterEnum(NestedEnum nv) nestedValue = nv;
private enum NestedEnum
X, Y;
如果我从嵌套枚举中删除私有修饰符,那么代码就可以工作。为什么 GWT 不允许嵌套枚举的私有修饰符?有解决办法吗?
【问题讨论】:
你试过让它静态吗? 这真的很酷! JLS(第 8.9 节)明确指出“嵌套枚举类型是隐式静态的。允许将嵌套枚举类型显式声明为静态。”这不适用于嵌套在enum
s 中的enum
s 还是GWT 编译器中的一个小缺陷?
...而 GWT 编译器仅使用 Eclipse 编译器 (ECJ) 来解析源代码并构建 AST。因此,要么 Eclipse 编译器有一个错误,即没有将枚举暴露为静态,要么 GWT 有一个错误,即没有为嵌套枚举推断静态标志(我会选择 ECJ,但这真的取决于他们的意图;它可能是设计使然)。
....好吧,我觉得自己很愚蠢....以前的构建中有一些东西挂在上面,结果证明将其设为静态并没有什么不同...。回到图纸木板。对不起各位!
您使用的是什么 GWT 版本?在 GWT 2.4.0 中,您的示例可以正常工作。
【参考方案1】:
序列化工作得很好,至少在您提供的示例中。所有枚举都以以下方式进行序列化/反序列化(GWT 2.4、2.3、2.2):
public static OuterEnum instantiate(SerializationStreamReader streamReader) throws SerializationException
int ordinal = streamReader.readInt();
OuterEnum[] values = OuterEnum.values();
assert (ordinal >= 0 && ordinal < values.length);
return values[ordinal];
public static void serialize(SerializationStreamWriter streamWriter, OuterEnum instance) throws SerializationException
assert (instance != null);
streamWriter.writeInt(instance.ordinal());
例如我不管里面用的是什么。只有序数通过网络传递。这意味着在其他地方存在问题,GWT 根本不关心枚举内部是什么,因为它不是通过网络传输的(枚举应该是不可变的,不需要传输其状态)。我认为您的问题可能是这样的:
public class OuterClass implements Serializable
private OuterEnum.NestedEnum nested;
private OuterEnum outer;
public enum OuterEnum
A(NestedEnum.X), B(NestedEnum.Y), C(NestedEnum.X);
NestedEnum nestedValue;
private OuterEnum(NestedEnum nv)
nestedValue = nv;
private enum NestedEnum
X, Y;
这个例子和之前的例子很不一样。假设在 GWT-RPC 服务中使用 OuterClass。由于 NestedEnum 用作 OuterClass 的字段,因此 GWT 需要为其创建一个 TypeSerializer。但是由于 TypeSerializer 是一个单独的类,它没有任何访问 NestedEnum 的权限(因为它是私有的)。所以编译失败。
这基本上是您的示例不起作用的唯一情况。在某些特定的 GWT 版本中可能存在一些错误,但我 100% 确定您的示例适用于 gwt 2.2-2.4。
【讨论】:
【参考方案2】:这可能与 javascript 有关。有可能/很可能在转换为 JavaScript 时,嵌套类被编写为非嵌套类。因此,如果它是私有的,则没有其他任何东西可以访问它。解决方法是不要将其设为私有,默认范围应该可以正常工作。
【讨论】:
这是一个好点,我没有想到这一点。理想情况下,我希望它是私有的......【参考方案3】:要成为 RPC 参数类类型,它必须有一个空的构造函数用于序列化。 所以我想,如果你添加
private OuterEnum()
// may be you should give a default value to nestedValue
它会起作用的!
【讨论】:
问题在于内部枚举的可见性。它可以很好地序列化外部枚举。这没有回答我的问题。以上是关于在 GWT-RPC 中使用嵌套枚举的主要内容,如果未能解决你的问题,请参考以下文章