2011-10-07 9 views
5

Tenemos una situación en la que usamos inyecciones basadas en JSR-330 para configurar nuestras aplicaciones independientes de Java 6, que funcionan muy bien para obtener parámetros de configuración en todas las capas .Uso de Guice 3 con JAX-WS en Java 6 fuera del contenedor web

También utilizamos los servicios web de JAX-WS durante bastante tiempo al utilizar la primera distribución autónoma de Metro con Java 5 dentro de un contenedor web, pero con Java 6 solo utilizamos la clase Endpoint para obtener una huella más pequeña.

así que ahora tengo una situación en la que tengo

  • un stand-alone Java 6 aplicación - sin contenedor de servlets (el embarcadero, Tomcat)
  • Un Guice 3 Inyector configurar como me gusta.
  • Un Endpoint manejando mi clase anotada @javax.jws.WebService que expone mis métodos como servicios web.

Me gustaría que los métodos del servicio web tengan sus campos @Inject manejados de forma transparente o para obtener acceso al inyector. I puede tomarlo como un campo estático del método principal, pero me gustaría una solución más limpia.

¿Alguna sugerencia?

(que entiendo de JAX-WS and Guice 3 que el módulo http://jax-ws-commons.java.net/guice/ no funciona con Guice 3, y la solución sugerida es Tomcat específico)

¿Le JSR-250 @Resource anotaciones ser útil en este caso?

+0

Resultó que puedo recibir al por ahora mediante la inyección de un proveedor en el objeto de aplicación como yo no necesita una inyección profundamente anidada. Bounty premiado para responder haciéndome darme cuenta de esto. –

Respuesta

5

No estoy seguro de haber entendido todo lo de la pregunta. Parece demasiado fácil para +500 recompensas. Por favor, publique un código si eso no es lo que está buscando.

De todos modos, una solución simple que crea un servicio web con la inyección de dependencias:

final Module module = new HelloModule(); 
final Injector injector = Guice.createInjector(module); 
final HelloService helloService = injector.getInstance(HelloService.class); 

Endpoint.publish("http://localhost:8080/helloService", helloService); 

A continuación una solución más sofisticada con la exploración ruta de clase (Reflections) basado en el código de Marcus Eriksson de JAX-WS Guice integration. Publica todas las clases que están anotadas con @GuiceManaged como un servicio web con Endpoint.publish().

private void initGuicedWebservices(final String packageNamePrefix) 
     throws Exception { 
    final Reflections reflections = new Reflections(packageNamePrefix); 
    final Set<Class<?>> guiceManaged = 
     reflections.getTypesAnnotatedWith(GuiceManaged.class); 
    for (final Class<?> clazz : guiceManaged) { 
     doGuice(clazz); 
    } 
} 

private void doGuice(final Class<?> clazz) throws Exception { 
    final GuiceManaged guiceManagedAnnotation = 
     clazz.getAnnotation(GuiceManaged.class); 

    final Injector injector = createInjector(guiceManagedAnnotation); 

    final Object serviceObject = clazz.newInstance(); 
    injector.injectMembers(serviceObject); 

    final String address = guiceManagedAnnotation.address(); 

    Endpoint.publish(address, serviceObject); 
} 

private Injector createInjector(final GuiceManaged guiceManagedAnnotation) 
     throws Exception { 
    final Class<? extends Module>[] moduleClasses = 
     guiceManagedAnnotation.module(); 

    final List<Module> moduleInstances = new ArrayList<Module>(); 
    for (final Class<? extends Module> moduleClass : moduleClasses) { 
     moduleInstances.add(moduleClass.newInstance()); 
    } 

    return Guice.createInjector(moduleInstances); 
} 

El GuiceManaged anotación:

@Retention(RUNTIME) 
@Target(TYPE) 
@Documented 
public @interface GuiceManaged { 
    public Class<? extends Module>[] module(); 
    public String address(); 
} 

Y el HelloServiceImpl fragmento:

@GuiceManaged(module = HelloModule.class, 
    address = "http://localhost:8080/helloService") 
@WebService 
public class HelloServiceImpl implements HelloService { 

    @Inject // bound in HelloModule 
    public GreetingsService greetingsService; 

    @Override 
    @WebMethod 
    public String sayHello(final String name) { 
     return greetingsService.sayHello(name); 
    } 
} 
+1

Después de reflexionar un poco sobre su respuesta, me di cuenta de que el mecanismo de punto final no hace nada nuevo, pero simplemente llame al método anotado @WebMethod. Esto significa que puedo salir adelante por ahora solo con la inyección de proveedores en la instancia. Como siempre, algunas preguntas solo son difíciles hasta que sepa cómo hacerlo. –

+1

También uso frecuentemente la recompensa de 500 puntos para atraer la atención a una pregunta. Si otros encuentran la pregunta simple y la respuesta trivial, me parece bien. –

0

necesita utilizar el punto de extensión AbstractMultiInstanceResolver.

crear la anotación GuiceManaged;

@Retention(RUNTIME) 
@Target(TYPE) 
@Documented 
@WebServiceFeatureAnnotation(id=GuiceManagedFeature.ID, bean=GuiceManagedFeature.class) 
@InstanceResolverAnnotation(GuiceManagedInstanceResolver.class) 
public @interface GuiceManaged { 
} 

aplicar la GuiceManagedFeature que es WebServiceFeature:

public class GuiceManagedFeature extends WebServiceFeature { 
    public static final String ID="FEATURE_GuiceManaged"; 

    @FeatureConstructor 
    public GuiceManagedFeature() 
    { 
     this.enabled=true; 
    } 

    public String getID() { 
     return ID; 
    } 
} 

Implementar InstanceResolver Extendiendo AbstractMultiInstanceResolver

public class GuiceManagedInstanceResolver extends AbstractMultiInstanceResolver { 
    private T instance=null; 
    public GuiceManagedInstanceResolver(@NotNull Class clazz) 
    { 
     super(clazz); 
    } 
    public T resolve(@NotNull Packet request) { 
     if(instance==null) 
     { 
      instance=create(); 
      Injector injector= Guice.createInjector(new WebServiceModule()); 
      injector.injectMembers(instance); 
     } 
     return instance; 
    } 
} 

Ahora Anote en su servicio con @GuiceManaged & uso @Inject para DI nivel de método del método de negocio .

+0

¿Se inspiró en http://developian.blogspot.com/2008/11/google-guice-and-jax-ws.html? –

+0

@ ThorbjørnRavnAndersen Sí, hace mucho tiempo, tuvimos un problema como el suyo y tratamos de usar ese blog como referencia, luego encontramos Guice-Fruit con Guice 2.x. –

+0

¿Esto significa que ahora usa Guice-Fruit y tiene que quedarse con Guice 2? –

Cuestiones relacionadas