Jersey and HK2 ServiceLocator

后端 未结 2 1081
自闭症患者
自闭症患者 2021-01-06 11:41

I\'m trying to initialize some components in my Jersey application in the Application constructor (the thing that inherits from ResourceConfig) . It looks like this

相关标签:
2条回答
  • 2021-01-06 12:07

    I am going to assume you are starting up a servlet and have a class extending org.glassfish.jersey.server.ResourceConfig and your bindings are correctly registered (e.g. using a Binder and registerInstances). If you then want to access the ServiceLocator in order to perform additional initialization, you have two choices:

    One approach is to register a ContainerLifecycleListener (as seen here in this post):

    // In Application extends ResourceConfig constructor
    register(new ContainerLifecycleListener() {
    
            @Override
            public void onStartup(final Container container) {
                // access the ServiceLocator here
                final ServiceLocator serviceLocator = container.getApplicationHandler().getInjectionManager().getInstance(ServiceLocator.class);
    
                // Perform whatever with serviceLocator
            }
    
            @Override
            public void onReload(final Container container) {
                /* ... */}
    
            @Override
            public void onShutdown(final Container container) {
                /* ... */}
        });
    

    The second approach is to use a Feature, which can also be auto-discovered using @Provider:

    @Provider
    public final class StartupListener implements Feature {
    
        private final ServiceLocator sl;
    
        @Inject
        public ProvisionStartupListener(final ServiceLocator sl) {
            this.sl = sl;
        }
    
        @Override
        public boolean configure(final FeatureContext context) {
            // Perform whatever action with serviceLocator
            return true;
        }
    
    0 讨论(0)
  • 2021-01-06 12:14

    How are you starting up your container? If you are using ApplicationHandler, you can just call:handler.getServiceLocator(). The ServiceLocator is, indeed, what you want to be using to access your dependencies.

    If you are starting up a servlet, I found that the best way to get access to the service locator was to have a Jersey feature set it on my startup class:

        private static final class LocatorSetFeature implements Feature {
    
        private final ServiceLocator scopedLocator;
    
        @Inject
        private LocatorSetFeature(ServiceLocator scopedLocator) {
            this.scopedLocator = scopedLocator;
        }
    
        @Override
        public boolean configure(FeatureContext context) {
            locator = this.scopedLocator; // this would set our member locator variable
            return true;
        }
    }
    

    The feature would just be registered with our resource config with config.register(new LocatorSetFeature()).

    It would be important to tie in startup of other components based on the lifecycle of your container, so this still feels a bit hacky. You might consider adding those classes as first class dependencies in the HK2 container and simply injecting the appropriate dependencies into your third party classes (using a Binder, for example).

    0 讨论(0)
提交回复
热议问题