2011-10-18 8 views
10

ネストした列挙型(私はプライベートにしたい)を持つ列挙型を持っていますが、GWTはネストした列挙型が表示されず、例外をスローすると伝えます。私はネストされた列挙型からprivate修飾子を削除した場合GWT-RPCでネストされた列挙型を使用する

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は入れ子になったenumのprivate修飾子を許可しないのですか?回避策はありますか?

+2

静的にしましたか? –

+0

これは本当にクールです! JLS(8.9節)では、「ネストされた列挙型は暗黙的に静的です。ネストされた列挙型を静的に明示的に宣言することは許されています。それは 'enum'にネストされた' enum'には当てはまりませんか?それともGWTコンパイラの小さな欠陥ですか? –

+0

... GWTコンパイラはEclipseコンパイラ(ECJ)を使用してソースコードを解析し、ASTを構築するだけです。だから、Eclipseコンパイラには、静的であるとして列挙型を公開しないバグがあります。あるいは、GWTはネストされた列挙型の静的フラグを推測しないというバグを持っています(ECJに行くでしょうが、デザインによるものかもしれない)。 –

答えて

2

シリアル化は、少なくともあなたが提供している例でうまくいきます。すべてが列挙型になっシリアライズさ/道(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はネットワーク上で転送されないため、GWTは列挙型の内部を気にしません(enumは状態を転送する必要はありません)。あなたの問題は次のようなものだと思います。

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; 
     } 
    } 
} 

この例は以前の例と非常に異なっています。 OuterClassがGWT-RPCサービスで使用されていると仮定しましょう。 NestedEnumはOuterClassのフィールドとして使用されるため、GWTはTypeSerializerを作成する必要があります。しかし、TypeSerializerは別のクラスであるため、NestedEnumへのアクセス権はありません(プライベートなので)。コンパイルに失敗します。

これは基本的に、あなたの例がうまくいかない場合です。いくつかの特定のGWTバージョンにいくつかのバグがあるかもしれませんが、私は100%あなたの例がgwt 2.2-2.4で動作することを確信しています。

0

これはおそらくJavaScriptと関係があります。 JavaScriptへの変換では、ネストされたクラスはネストされていないものとして記述されている可能性があります。したがって、それが私的なものであれば、誰もそれにアクセスすることはできません。回避策はそれをプライベートにしないことです、デフォルトスコープはうまく動作するはずです。

+0

それは良い点です、私はそれを考えていませんでした。理想的に私はそれがプライベートであることを望みます... – luketorjussen

-2

RPCパラメータクラス型であるためには、シリアル化のための空のコンストラクタが必要です。 だから私はあなたが

private OuterEnum(){ 
// may be you should give a default value to nestedValue 
} 

を追加する場合、それは動作します、と思います!

+0

問題は内部列挙体の可視性にあります。これは私の質問には答えません。 – luketorjussen

関連する問題