2012-09-12 13 views
5

Meine enums werden als int in mongodb (von C# app) gespeichert. Jetzt, in Java, wenn ich versuche, sie abzurufen, löst es eine Ausnahme aus (es scheint, dass Enum nur vom Zeichenfolgenwert konvertiert werden kann). Kann ich es irgendwie schaffen?Spring -Mongodb speichern/abrufen enums als int nicht string

Auch wenn ich einige Sammlungen in mongodb (aus Java) speichern, konvertiert es Enum-Werte in Zeichenfolge (nicht ihren Wert/Kardinal). Gibt es eine Überschreibung?

Dies kann erreicht werden, indem man mongodb-converter auf Klassenebene schreibt, aber ich möchte nicht für jede Klasse mondodb-converter schreiben, da diese Enums in vielen verschiedenen Klassen sind.

Haben wir etwas auf der Feldebene?

Antwort

8

Nach einem langen Graben im Frühjahr-mongodb Konverter Code, Ok ich fertig und jetzt ist es funktioniert :) hier ist es (wenn es einfachere Lösung ist, werde ich glücklich sein, wie gut sehen, das ist was ich getan habe):

zuerst definieren:

public interface IntEnumConvertable { 
     public int getValue();  

}

und eine einfache Enumeration, die Arbeitsgeräte es:

public enum tester implements IntEnumConvertable{ 
    vali(0),secondvali(1),thirdvali(5); 

    private final int val; 
    private tester(int num) 
    { 
     val = num;   
    } 
    public int getValue(){ 
     return val; 
    } 
} 

Ok, jetzt werden Sie jetzt brauchen, 2 Konverter, ist einfach, die andere komplexer ist. der einfache (dieses einfache Baby behandelt auch die einfache Konvertierung und gibt eine Zeichenfolge zurück, wenn das Umwandeln nicht möglich ist, das ist großartig, wenn Enum als Zeichenfolgen gespeichert werden soll und enum Zahlen sind, die als Ganzzahlen gespeichert werden):

public class IntegerEnumConverters { 
    @WritingConverter 
    public static class EnumToIntegerConverter implements Converter<Enum<?>, Object> { 
     @Override 
     public Object convert(Enum<?> source) { 
      if(source instanceof IntEnumConvertable) 
      { 
       return ((IntEnumConvertable)(source)).getValue(); 
      } 
      else 
      { 
       return source.name(); 
      }    
     } 
    } 
} 

desto komplexer ein, ist eigentlich ein Konverter Werk:

public class IntegerToEnumConverterFactory implements ConverterFactory<Integer, Enum> { 
     @Override 
     public <T extends Enum> Converter<Integer, T> getConverter(Class<T> targetType) { 
      Class<?> enumType = targetType; 
      while (enumType != null && !enumType.isEnum()) { 
       enumType = enumType.getSuperclass(); 
      } 
      if (enumType == null) { 
       throw new IllegalArgumentException(
         "The target type " + targetType.getName() + " does not refer to an enum"); 
      } 
      return new IntegerToEnum(enumType); 
     } 
     @ReadingConverter 
     public static class IntegerToEnum<T extends Enum> implements Converter<Integer, Enum> { 
      private final Class<T> enumType; 

      public IntegerToEnum(Class<T> enumType) { 
       this.enumType = enumType; 
      } 

      @Override 
      public Enum convert(Integer source) { 
        for(T t : enumType.getEnumConstants()) { 
         if(t instanceof IntEnumConvertable) 
         { 
          if(((IntEnumConvertable)t).getValue() == source.intValue()) { 
           return t; 
          }       
         }      
        } 
        return null; 
      } 
     } 
} 

und jetzt für den Hack Teil, i personnaly any „programmitacly“ Art und Weise nur knapp sein Ziel findet eine Konverter Fabrik innerhalb eines mongoConverter, so i zu registrieren in den Code gegraben und mit ein wenig Casting, hier ist es (setzen Sie diese 2 Babys Funktionen in Ihre @Configuration-Klasse)

+1

Danke. Ich habe eine Idee verwendet, um LowerStringToEnumConverter zu implementieren – Demwis

+1

Vielen Dank! Es ist sehr verdrahtet, dass die Frühjahrsdaten keine einfache Möglichkeit bieten, das zu tun. – ruX

+0

Das war sehr hilfreich. –

2

Sie müssen Ihre benutzerdefinierten Konverter implementieren und sie mit Feder registrieren.

http://static.springsource.org/spring-data/data-mongo/docs/current/reference/html/#mongo.custom-converters

+0

das funktioniert auf Klassenebene .. ich will das nicht ** bereits erwähnt dies in der Frage – gsagrawal

+0

nicht bemerkt (formatieren Sie Ihre Frage bitte, schwer zu lesen) - haben Sie es versucht. Ich denke, es funktioniert auch für Felder. – gkamal

+2

Die andere Option besteht darin, einen weiteren Getter/Setter für Ints zu Ihrer Entität hinzuzufügen, die die Konvertierung durchführt. Der Getter/Setter für die Enumeration sollte als @Transient markiert sein. – gkamal