Джерси 2 + HK2 - @ApplicationScoped не работает

у меня урок

@ApplicationScoped
public class Service{
 private Map<String, Integer> something ;
 private final Logger LOGGER = LoggerFactory.getLogger(Service.class);

 @PostConstruct
 public void initialize(){
    something = new HashMap<>();
 }

 public void increase(String userName){
    something.put(userName, something.getOrDefault(userName, 0) + 1);
 }

 public Map<String, Integer> getSomething(){
    return this.something;
 }

 public Integer getSomethingForUser(String userName){
    return something.getOrDefault(userName, 0);
 }
}

Который я хочу быть глобально одним экземпляром.

Проблема в том, что когда я ввожу эту службу в два разных места, у меня есть два разных экземпляра службы, что приводит к тому, что всегда возвращается счетчик 0. .toString() возвращает следующее:

package.services.Service@492e4f4b
package.services.Service@4bc86c4d

Я создал этот сервис, чтобы протестировать свою реализацию HK2-Jersey, которая, по-видимому, не работает должным образом.

Веб.xml:

<servlet-name>jersey-serlvet</servlet-name>
    <servlet-class>org.glassfish.jersey.servlet.ServletContainer</servlet-class>
    <init-param>
         <param-name>jersey.config.server.provider.packages</param-name>
         <param-value>io.swagger.jaxrs.listing,mypackage.rest</param-value>
    </init-param>
     <init-param>
        <param-name>jersey.config.server.provider.classnames</param-name>
        <param-value>
            io.swagger.jaxrs.listing.ApiListingResource,
            io.swagger.jaxrs.listing.SwaggerSerializers
        </param-value>
    </init-param>
    <init-param>
        <param-name>javax.ws.rs.Application</param-name>
        <param-value>mypackage.config.ApplicationConfiguration</param-value>
      </init-param>
    <load-on-startup>1</load-on-startup>
</servlet>

<servlet-mapping>
    <servlet-name>jersey-serlvet</servlet-name>
    <url-pattern>/rest/*</url-pattern>
</servlet-mapping>

Конфигурация приложения.java:

public class ApplicationConfiguration extends ResourceConfig {
public ApplicationConfiguration() {
     register(new AbstractBinder() {
         @Override
         protected void configure() {
             bind(Service.class).to(Service.class);    
         }
     });

    packages(true, "com.mypackage.rest");
}

}

Без этой функции bind сервер выдает исключение, что @Inject не удовлетворено.

Кто-нибудь может указать, что не так?


person deem    schedule 12.06.2016    source источник


Ответы (1)


В HK2 нет такой вещи, как @ApplicationScoped. Это только CDI (который отличается). В HK2 есть одноэлементный прицел. С вашей конфигурацией вы можете либо сделать

bind(new Service()).to(Service.class); 

который автоматически сделает его синглтоном. Единственная проблема заключается в том, что вы теряете любую инъекцию контейнером (если она вам требуется). Другой способ - установить область видимости в методе in(Scope).

bind(Service.class).to(Service.class).in(Singleton.class); 

Это javax.inject.Singleton.

person Paul Samsotha    schedule 12.06.2016
comment
Спасибо, сработало как шарм. Не могли бы вы сказать, есть ли какой-либо автоматический способ связать эти классы или мне нужно добавить их сюда вручную? - person deem; 12.06.2016
comment
Если вы хотите задать еще один вопрос, я буду рад ответить на него. - person Paul Samsotha; 13.06.2016
comment
Я думаю, что в Джерси есть собственное определение @ApplicationScoped. Причина, по которой вы могли видеть разные экземпляры, заключается в том, что это прокси-область, и поэтому внедренные прокси-серверы отличаются, даже если базовые фактические службы, которые вы получите, одинаковы (используйте равенство, а не == для сравнения) - person jwells131313; 13.06.2016
comment
@peeskillet, как вы просили, я создал новый вопрос: stackoverflow.com/questions/37794144/. Большое спасибо за помощь. - person deem; 13.06.2016