Skip to content

Commit

Permalink
Allow to set the metrics factory programmatically on MetricsOptions - f…
Browse files Browse the repository at this point in the history
…ixes #1432
  • Loading branch information
vietj committed May 23, 2016
1 parent 2b6a3df commit 03a493f
Show file tree
Hide file tree
Showing 14 changed files with 210 additions and 139 deletions.
3 changes: 3 additions & 0 deletions src/main/asciidoc/java/index.adoc
Expand Up @@ -871,6 +871,9 @@ to the classpath. The metrics SPI is an advanced feature which allows implemente
order to gather metrics. For more information on this, please consult the
`link:../../apidocs/io/vertx/core/spi/metrics/VertxMetrics.html[API Documentation]`.

You can also specify a metrics factory programmatically if embedding Vert.x using
`link:../../apidocs/io/vertx/core/metrics/MetricsOptions.html#setFactory-io.vertx.core.spi.VertxMetricsFactory-[setFactory]`.

== OSGi

Vert.x Core is packaged as an OSGi bundle, so can be used in any OSGi R4.2+ environment such as Apache Felix
Expand Down
14 changes: 7 additions & 7 deletions src/main/java/io/vertx/core/VertxOptions.java
Expand Up @@ -132,7 +132,7 @@ public class VertxOptions {
private boolean haEnabled = DEFAULT_HA_ENABLED;
private int quorumSize = DEFAULT_QUORUM_SIZE;
private String haGroup = DEFAULT_HA_GROUP;
private MetricsOptions metrics = new MetricsOptions();
private MetricsOptions metricsOptions = new MetricsOptions();
private long warningExceptionTime = DEFAULT_WARNING_EXCEPTION_TIME;
private EventBusOptions eventBusOptions = new EventBusOptions();
private HostnameResolverOptions hostnameResolverOptions = new HostnameResolverOptions();
Expand All @@ -159,7 +159,7 @@ public VertxOptions(VertxOptions other) {
this.haEnabled = other.isHAEnabled();
this.quorumSize = other.getQuorumSize();
this.haGroup = other.getHAGroup();
this.metrics = other.getMetricsOptions() != null ? new MetricsOptions(other.getMetricsOptions()) : null;
this.metricsOptions = other.getMetricsOptions() != null ? new MetricsOptions(other.getMetricsOptions()) : null;
this.warningExceptionTime = other.warningExceptionTime;
this.eventBusOptions = new EventBusOptions(other.eventBusOptions);
this.hostnameResolverOptions = other.hostnameResolverOptions != null ? new HostnameResolverOptions() : null;
Expand Down Expand Up @@ -574,7 +574,7 @@ public VertxOptions setHAGroup(String haGroup) {
* @return the metrics options
*/
public MetricsOptions getMetricsOptions() {
return metrics;
return metricsOptions;
}

/**
Expand All @@ -584,7 +584,7 @@ public MetricsOptions getMetricsOptions() {
* @return a reference to this, so the API can be used fluently
*/
public VertxOptions setMetricsOptions(MetricsOptions metrics) {
this.metrics = metrics;
this.metricsOptions = metrics;
return this;
}

Expand Down Expand Up @@ -671,7 +671,7 @@ public boolean equals(Object o) {
return false;
if (hostnameResolverOptions != null ? !hostnameResolverOptions.equals(that.hostnameResolverOptions) : that.hostnameResolverOptions != null)
return false;
return !(metrics != null ? !metrics.equals(that.metrics) : that.metrics != null);
return !(metricsOptions != null ? !metricsOptions.equals(that.metricsOptions) : that.metricsOptions != null);

}

Expand All @@ -687,7 +687,7 @@ public int hashCode() {
result = 31 * result + (haEnabled ? 1 : 0);
result = 31 * result + quorumSize;
result = 31 * result + (haGroup != null ? haGroup.hashCode() : 0);
result = 31 * result + (metrics != null ? metrics.hashCode() : 0);
result = 31 * result + (metricsOptions != null ? metricsOptions.hashCode() : 0);
result = 31 * result + (eventBusOptions != null ? eventBusOptions.hashCode() : 0);
result = 31 * result + (hostnameResolverOptions != null ? hostnameResolverOptions.hashCode() : 0);
result = 31 * result + (int) (warningExceptionTime ^ (warningExceptionTime >>> 32));
Expand All @@ -707,7 +707,7 @@ public String toString() {
", haEnabled=" + haEnabled +
", quorumSize=" + quorumSize +
", haGroup='" + haGroup + '\'' +
", metrics=" + metrics +
", metrics=" + metricsOptions +
", hostnameResolver=" + hostnameResolverOptions.toJson() +
", eventbus=" + eventBusOptions.toJson() +
", warningExceptionTime=" + warningExceptionTime +
Expand Down
15 changes: 10 additions & 5 deletions src/main/java/io/vertx/core/impl/VertxImpl.java
Expand Up @@ -363,14 +363,19 @@ public DnsClient createDnsClient(int port, String host) {

private VertxMetrics initialiseMetrics(VertxOptions options) {
if (options.getMetricsOptions() != null && options.getMetricsOptions().isEnabled()) {
ServiceLoader<VertxMetricsFactory> factories = ServiceLoader.load(VertxMetricsFactory.class);
if (factories.iterator().hasNext()) {
VertxMetricsFactory factory = factories.iterator().next();
VertxMetricsFactory factory = options.getMetricsOptions().getFactory();
if (factory == null) {
ServiceLoader<VertxMetricsFactory> factories = ServiceLoader.load(VertxMetricsFactory.class);
if (factories.iterator().hasNext()) {
factory = factories.iterator().next();
} else {
log.warn("Metrics has been set to enabled but no VertxMetricsFactory found on classpath");
}
}
if (factory != null) {
VertxMetrics metrics = factory.metrics(this, options);
Objects.requireNonNull(metrics, "The metric instance created from " + factory + " cannot be null");
return metrics;
} else {
log.warn("Metrics has been set to enabled but no VertxMetricsFactory found on classpath");
}
}
return new DummyVertxMetrics();
Expand Down
33 changes: 33 additions & 0 deletions src/main/java/io/vertx/core/metrics/MetricsOptions.java
Expand Up @@ -18,6 +18,7 @@

import io.vertx.codegen.annotations.DataObject;
import io.vertx.core.json.JsonObject;
import io.vertx.core.spi.VertxMetricsFactory;

/**
* Vert.x metrics base configuration, this class can be extended by provider implementations to configure
Expand All @@ -35,6 +36,7 @@ public class MetricsOptions {

private boolean enabled;
private JsonObject json; // Keep a copy of the original json, so we don't lose info when building options subclasses
private VertxMetricsFactory factory;

/**
* Default constructor
Expand All @@ -50,6 +52,7 @@ public MetricsOptions() {
*/
public MetricsOptions(MetricsOptions other) {
enabled = other.isEnabled();
factory = other.factory;
}

/**
Expand Down Expand Up @@ -83,6 +86,36 @@ public MetricsOptions setEnabled(boolean enable) {
return this;
}

/**
* Get the metrics factory to be used when metrics are enabled.
* <p>
* If the metrics factory has been programmatically set here, then that will be used when metrics are enabled
* for creating the {@link io.vertx.core.spi.metrics.VertxMetrics} instance.
* <p>
* Otherwise Vert.x attempts to locate a metrics factory implementation on the classpath.
*
* @return the metrics factory
*/
public VertxMetricsFactory getFactory() {
return factory;
}

/**
* Programmatically set the metrics factory to be used when metrics are enabled.
* <p>
* Only valid if {@link MetricsOptions#isEnabled} = true.
* <p>
* Normally Vert.x will look on the classpath for a metrics factory implementation, but if you want to set one
* programmatically you can use this method.
*
* @param factory the metrics factory
* @return a reference to this, so the API can be used fluently
*/
public MetricsOptions setFactory(VertxMetricsFactory factory) {
this.factory = factory;
return this;
}

public JsonObject toJson() {
return json != null ? json.copy() : new JsonObject();
}
Expand Down
3 changes: 3 additions & 0 deletions src/main/java/io/vertx/core/package-info.java
Expand Up @@ -778,6 +778,9 @@
* order to gather metrics. For more information on this, please consult the
* {@link io.vertx.core.spi.metrics.VertxMetrics API Documentation}.
*
* You can also specify a metrics factory programmatically if embedding Vert.x using
* {@link io.vertx.core.metrics.MetricsOptions#setFactory(io.vertx.core.spi.VertxMetricsFactory)}.
*
* == OSGi
*
* Vert.x Core is packaged as an OSGi bundle, so can be used in any OSGi R4.2+ environment such as Apache Felix
Expand Down
Expand Up @@ -26,17 +26,15 @@
/**
* @author <a href="mailto:julien@julienviet.com">Julien Viet</a>
*/
public class ConfigurableMetricsFactory implements VertxMetricsFactory {

public static VertxMetricsFactory delegate;
public class CustomMetricsFactory implements VertxMetricsFactory {

@Override
public VertxMetrics metrics(Vertx vertx, VertxOptions options) {
return delegate != null ? delegate.metrics(vertx, options) : new DummyVertxMetrics();
return new DummyVertxMetrics();
}

@Override
public MetricsOptions newOptions() {
return delegate != null ? delegate.newOptions() : new MetricsOptions();
return new CustomMetricsOptions();
}
}
12 changes: 1 addition & 11 deletions src/test/java/io/vertx/test/core/HttpMetricsTest.java
Expand Up @@ -45,20 +45,10 @@
*/
public class HttpMetricsTest extends HttpTestBase {

@BeforeClass
public static void setFactory() {
ConfigurableMetricsFactory.delegate = new FakeMetricsFactory();
}

@AfterClass
public static void unsetFactory() {
ConfigurableMetricsFactory.delegate = null;
}

@Override
protected VertxOptions getOptions() {
VertxOptions options = super.getOptions();
options.setMetricsOptions(new MetricsOptions().setEnabled(true));
options.setMetricsOptions(new MetricsOptions().setEnabled(true).setFactory(new FakeMetricsFactory()));
return options;
}

Expand Down
31 changes: 11 additions & 20 deletions src/test/java/io/vertx/test/core/LauncherTest.java
Expand Up @@ -462,30 +462,21 @@ private void clearProperties() {

@Test
public void testCustomMetricsOptions() throws Exception {
System.setProperty(RunCommand.METRICS_OPTIONS_PROP_PREFIX + "enabled", "true");
System.setProperty(RunCommand.METRICS_OPTIONS_PROP_PREFIX + "customProperty", "customPropertyValue");
MyLauncher launcher = new MyLauncher();
String[] args = {"run", "java:" + TestVerticle.class.getCanonicalName()};
ClassLoader oldCL = Thread.currentThread().getContextClassLoader();
Thread.currentThread().setContextClassLoader(MetricsOptionsTest.createMetricsFromMetaInfLoader("io.vertx.test.core.CustomMetricsFactory"));
try {
ConfigurableMetricsFactory.delegate = new VertxMetricsFactory() {
@Override
public VertxMetrics metrics(Vertx vertx, VertxOptions options) {
return new DummyVertxMetrics();
}

@Override
public MetricsOptions newOptions() {
return new CustomMetricsOptions();
}
};
System.setProperty(RunCommand.METRICS_OPTIONS_PROP_PREFIX + "enabled", "true");
System.setProperty(RunCommand.METRICS_OPTIONS_PROP_PREFIX + "customProperty", "customPropertyValue");
MyLauncher launcher = new MyLauncher();
String[] args = {"run", "java:" + TestVerticle.class.getCanonicalName()};
launcher.dispatch(args);
waitUntil(() -> TestVerticle.instanceCount.get() == 1);
VertxOptions opts = launcher.getVertxOptions();
CustomMetricsOptions custom = (CustomMetricsOptions) opts.getMetricsOptions();
assertEquals("customPropertyValue", custom.getCustomProperty());
} finally {
ConfigurableMetricsFactory.delegate = null;
Thread.currentThread().setContextClassLoader(oldCL);
}
waitUntil(() -> TestVerticle.instanceCount.get() == 1);
VertxOptions opts = launcher.getVertxOptions();
CustomMetricsOptions custom = (CustomMetricsOptions) opts.getMetricsOptions();
assertEquals("customPropertyValue", custom.getCustomProperty());
}

@Test
Expand Down

0 comments on commit 03a493f

Please sign in to comment.