2016-06-29 4 views
1

Was ist ein ContextResolver in Jersey und was ist ein Provider? Was ist der Unterschied zwischen den beiden? Ich benutze Genson mit Jersey. Genson wird automatisch registriert, wenn Jersey das Genson JAR auf dem Klassenpfad findet. Das WEB-INF/services-Verzeichnis des Genson JAR enthält eine Datei namens "org.glassfish.jersey.internal.spi.AutoDiscoverable".Was ist ein ContextResolver und Provider in Jersey?

Im Anschluss daran AutoDiscoverable Pfad standardmäßig Genson/Jersey Auto-Register eine der folgenden Klasse:

@Provider 
@Consumes({MediaType.APPLICATION_JSON, "text/json", "application/*+json"}) 
@Produces({MediaType.APPLICATION_JSON, "text/json", "application/*+json"}) 
public class GensonJsonConverter implements MessageBodyReader<Object>, MessageBodyWriter<Object> { 

    private final ContextResolver<GensonJaxRSFeature> _gensonResolver; 

Hier ist, wo mehr Verwirrung ins Spiel kommt: Blick auf die Dokumentation Genson es einen speziellen Provider zu erstellen empfiehlt wie so:

@Provider 
    public class GensonProvider implements ContextResolver<Genson> { 
    private final Genson genson = new GensonBuilder().setSkipNull(true).create(); 
    } 

jedoch, dass Provider implementiert eine ContextResolver kein MessageBodyReader/Writer wie die interne Genson man tut. Was ist der Unterschied? Auch dieser Anbieter tut nicht tun das gleiche wie die Standard-Auto-registriert man tut! Insbesondere ignoriert es ignoriert JAXB Tags wie @XmlTransient! Graben in den Code Genson Quelle für GensonJaxRSFeature, ich sehe, dass das Genson Objekt wie so erstellt:

private static final Genson _defaultGenson = new GensonBuilder() 
     .withBundle(new JAXBBundle()) 
     .useConstructorWithArguments(true) 
     .create(); 

Daraus und aus der Dokumentation Genson ich sehen kann, dass die „JAXBBundle“ ist wahrscheinlich das, was Genson verursacht Aufmerksamkeit zu schenken zu den JAXB-Anmerkungen.

Das Hauptproblem:

Ich möchte den Standard Genson JSON-Anbieter verwenden, die mit Jersey Auto-registriert ist, aber ich möchte ein paar benutzerdefinierte Eigenschaften auf sie einzustellen. Wie gesagt, wenn ich meinen benutzerdefinierten Provider registriere, wird nicht der Standard-Genson verwendet!


Update:

Dies ist, was jetzt ich mache und es funktioniert. Die Lösung von @eugen ist jedoch die von Genson empfohlene Lösung.

+0

Was sagen Sie, dass Genson empfiehlt, einen benutzerdefinierten Anbieter zu definieren? Zumindest empfiehlt die aktuelle Dokumentation, eine ResourceConfig zu verwenden, die mit einem GensonJaxRSFeature konfiguriert ist, das Ihre eigene Genson-Instanz verwendet. Sie sollten die Standard-Gensen-Instanz nicht ändern. Wenn Sie eine andere Konfiguration wünschen, erstellen Sie einfach eine andere Instanz mit der gewünschten Konfiguration. – eugen

+0

@eugen Sehen Sie sich meine Bearbeitung an, um zu sehen, was ich getan habe. Der in den Genson-Dokumenten empfohlene Code ist "new ResourceConfig(). Register (new GensonJaxRSFeature(). Use (myCustomGenson) .disableSerializationFor (String.class));". Es macht dasselbe wie das, was ich gerade mache, außer dass ich einen Provider verwende, anstatt wo immer du den "neuen ResourceConfig" -Code eingibst. Wohin geht diese "neue ResourceConfig" normalerweise?Können Sie ein Beispiel oder einen Link posten? – KyleM

+0

Überprüfen Sie [die offizielle Dokumentation] (https://jersey.java.net/documentation/latest/deployment.html#environmenmt.appmodel), wie Sie eine ResourceConfig verwenden können. Es gibt keine Möglichkeit, die standardmäßige genson-Instanz zu übernehmen und sie zu ändern. Stellen Sie einfach Ihre eigene Konfiguration zur Verfügung. Und ja, wenn Sie möchten, dass Genson die JAXB-Annotationen verwendet, müssen Sie es für die Verwendung dieses Bundles konfigurieren. – eugen

Antwort

2

Wie immer in unserer Welt für das gleiche Problem gibt es mehrere Lösungen. Jersey scheint die Verwendung von ResourceConfig zu fördern, anstatt benutzerdefinierte Anbieter zu definieren. So können Sie es mit einer Ressourcen-Konfiguration erreichen (aus der Jersey-Dokumentation here und der Genson-Dokumentation here).

public class MyApplication extends ResourceConfig { 
    public MyApplication() { 
     Genson genson = new GensonBuilder() 
       .withBundle(new JAXBBundle()) 
       .useConstructorWithArguments(true) 
       .setSkipNull(true) 
       .create(); 

     register(new GensonJaxRSFeature().use(genson)); 
    } 
} 

Aber natürlich ist die Art, wie Sie es mit einem Anbieter tun, auch in Ordnung.

+0

Danke, ich glaube, ich wurde gerade verwirrt b/c in den Genson-Dokumenten sagt es, um eine "neue ResourceConfig()" zu erstellen, was in dieser Lösung nicht der Fall ist. Sie erstellen einen neuen GensonBuilder, aber nie eine neue ResourceConfig(). Wie auch immer, ich bekomme es jetzt .. Ich habe hauptsächlich dafür gesorgt, dass ich mit dem "neuen ResourceConfig" Stück nichts Wichtiges verpasst habe ... – KyleM

+0

Nein, du verpasst nichts. Die Ressourcen-Konfiguration scheint der Ort zu sein, an dem wir von uns wollen, dass wir den Konfigurationsteil einstellen - aber Ihre derzeitige Lösung ist auch in Ordnung. Ja, hier erstellen wir keine Ressourcen-Konfiguration, sondern erweitern sie. In einigen anderen Verwendungen von Jersey Menschen würde es instanziieren (ich denke, es ist der Fall mit Steg + Jersey). – eugen

Verwandte Themen