【问题标题】:Vertx & HK2 - Launching the application (dependency injection)Vertx & HK2 - 启动应用程序(依赖注入)
【发布时间】:2017-10-16 09:22:54
【问题描述】:

我正在尝试使用 Vert.x 和 HK2 扩展来构建依赖注入的应用程序。但是,我似乎找不到任何可以向我展示全貌的示例。

请注意,我对依赖注入完全陌生。

我按照this example 中的说明进行操作,但是在启动应用程序时我得到了 NoSuchMethodException,因为它试图访问 Verticle 类 (SimpleVerticle) 中不存在的默认无参数构造函数。

在我的 build.gradle 中,mainClassName 设置为“io.vertx.core.Launcher”,而在 shadowJar 清单属性中,“Main-Verticle”设置为 SimpleVerticle,如示例所示。

我肯定在某处遗漏了一些东西。谁能告诉我我缺少什么或指出一些最新的完整示例?

  • Vert.x 版本:3.4.2
  • Vert.x HK2 版本:2.5.0

build.gradle:

buildscript {
    repositories {
        mavenCentral()
    }
}

plugins {
    id 'java'
    id 'application'
    id 'com.github.johnrengelman.shadow' version '1.2.3'
    id 'java-library'
    id 'eclipse'
    id 'idea'
    id 'maven'
    id 'groovy'
    id 'jacoco'
}


group 'example'
version "${buildVersion}"

repositories {
    mavenCentral()
}

sourceCompatibility = '1.8'
targetCompatibility = '1.8'

dependencies {
    compile('io.vertx:vertx-core:3.4.2')
    compile('io.vertx:vertx-web:3.4.2')
    compile('javax.json:javax.json-api:1.1')
    compile('org.glassfish:javax.json:1.0.4')
    compile('log4j:log4j:1.2.17')
    compile('io.vertx:vertx-web-client:3.4.2')
    compile('com.englishtown.vertx:vertx-hk2:2.5.0')
    testCompile "junit:junit:4.12"
    testCompile "io.vertx:vertx-unit:3.3.3"
    testCompile "com.jayway.restassured:rest-assured:2.4.0"
    testImplementation 'junit:junit:4.12'
}

mainClassName = 'io.vertx.core.Launcher'

shadowJar {
    classifier = 'fat'
    baseName = 'aggregator-api'
    manifest {
        attributes "Main-Verticle": 'example.startup.StartupVerticle'
    }
    mergeServiceFiles {
        include 'META-INF/services/io.vertx.core.spi.VerticleFactory'
    }
}

StartupVerticle:

package example.startup;

import example.config.ConfigReader;
import io.vertx.core.AbstractVerticle;

import javax.inject.Inject;

public class StartupVerticle extends AbstractVerticle {

    private final ConfigReader configReader;

    @Inject
    public StartupVerticle(final ConfigReader configReader) {
        this.configReader = configReader;
    }

    @Override
    public void start() throws Exception {
        if(this.configReader == null) throw new IllegalStateException("ConfigReader was not injected!");

        super.start();
        System.out.println("Started verticle using DI");
    }

}

配置绑定器:

package example.binder;

import example.config.ConfigReader;
import example.config.ConfigReaderImpl;
import org.glassfish.hk2.utilities.binding.AbstractBinder;

public class ConfigBinder extends AbstractBinder {

    @Override
    protected void configure() {
        this.bind(ConfigReaderImpl.class).to(ConfigReader.class);
    }

}

配置读取器:

package example.config;

import io.vertx.core.json.JsonObject;

public interface ConfigReader {

    JsonObject getConfig();

}

ConfigReaderImpl:

package example.config;

import io.vertx.core.json.JsonObject;

public class ConfigReaderImpl implements ConfigReader {

    private final JsonObject config;

    ConfigReaderImpl(JsonObject config) {
        this.config = config;
    }

    @Override
    public JsonObject getConfig() {
        return this.config;
    }

}

【问题讨论】:

  • 如果你不提供你已经尝试过的东西,别人怎么能指出丢失的部分?
  • 抱歉,我以为我已经解释的够多了。添加了当前代码。它基本上是我链接的 GitHub 示例的副本。
  • 感谢更新,请确保删除任何公司/组织提及(主要通过包名称):)
  • 感谢您的提示。已更新。

标签: java gradle dependency-injection vert.x hk2


【解决方案1】:

在我看来,您需要在某处实际创建 ServiceLocator。像这样的:

private void startServiceLocator() {
  ServiceLocatorUtilities.bind("MyServiceLocator", new ConfigBinder());
}

欲了解更多信息,请参阅bind

还有更多关于如何启动hk2的信息:Getting Started

【讨论】:

    【解决方案2】:

    设法修复它。

    我切换到 Guice 我为 ConfigReaderImpl 类的 JsonObject 注入遗漏了一些东西

    新的 ConfigBinder:

    public class ConfigBinder extends AbstractModule {
    
        private final String CONFIG_PATH = "config";
    
        @Override
        protected void configure() {
            this.bind(ConfigReader.class).to(ConfigReaderImpl.class).in(Scopes.NO_SCOPE);
            this.bindConfig(Vertx.currentContext().config(), this.CONFIG_PATH);
        }
    
        private void bindConfig(JsonObject config, String path) {
            this.bind(JsonObject.class).annotatedWith(Names.named(path)).toInstance(config);
        }
    
    }
    

    我还缺少 ConfigReaderImpl 类中的注释:

    public class ConfigReaderImpl implements ConfigReader {
    
        private final JsonObject config;
    
        @Inject
        private ConfigReaderImpl(@Named("config") final JsonObject config) {
            this.config = config;
        }
    
        @Override
        public JsonObject getConfig() {
            return this.config;
        }
    
    }
    

    我设法部署了一个依赖注入的 Verticle:

    Injector injector = Guice.createInjector(new ConfigBinder());
    Verticle verticle = injector.getInstance(SomeVerticle.class);
    this.getVertx().deployVerticle(verticle);
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-11-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多