Skip to content

Commit 369cd15

Browse files
committed
Merge pull request #22548 from AndrewDi
* pr/22548: Polish "Add basic auth support for Prometheus pushgateway" Add basic auth support for Prometheus pushgateway Closes gh-22548
2 parents 2c120eb + 14eb041 commit 369cd15

File tree

3 files changed

+78
-5
lines changed

3 files changed

+78
-5
lines changed

spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/export/prometheus/PrometheusMetricsExportAutoConfiguration.java

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
import io.micrometer.prometheus.PrometheusConfig;
2626
import io.micrometer.prometheus.PrometheusMeterRegistry;
2727
import io.prometheus.client.CollectorRegistry;
28+
import io.prometheus.client.exporter.BasicAuthHttpConnectionFactory;
2829
import io.prometheus.client.exporter.PushGateway;
2930
import org.apache.commons.logging.Log;
3031
import org.apache.commons.logging.LogFactory;
@@ -49,6 +50,7 @@
4950
import org.springframework.context.annotation.Configuration;
5051
import org.springframework.core.env.Environment;
5152
import org.springframework.core.log.LogMessage;
53+
import org.springframework.util.StringUtils;
5254

5355
/**
5456
* {@link EnableAutoConfiguration Auto-configuration} for exporting metrics to Prometheus.
@@ -124,11 +126,16 @@ public PrometheusPushGatewayManager prometheusPushGatewayManager(CollectorRegist
124126
String job = getJob(properties, environment);
125127
Map<String, String> groupingKey = properties.getGroupingKey();
126128
ShutdownOperation shutdownOperation = properties.getShutdownOperation();
127-
return new PrometheusPushGatewayManager(getPushGateway(properties.getBaseUrl()), collectorRegistry,
128-
pushRate, job, groupingKey, shutdownOperation);
129+
PushGateway pushGateway = initializePushGateway(properties.getBaseUrl());
130+
if (StringUtils.hasText(properties.getUsername())) {
131+
pushGateway.setConnectionFactory(
132+
new BasicAuthHttpConnectionFactory(properties.getUsername(), properties.getPassword()));
133+
}
134+
return new PrometheusPushGatewayManager(pushGateway, collectorRegistry, pushRate, job, groupingKey,
135+
shutdownOperation);
129136
}
130137

131-
private PushGateway getPushGateway(String url) {
138+
private PushGateway initializePushGateway(String url) {
132139
try {
133140
return new PushGateway(new URL(url));
134141
}

spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/export/prometheus/PrometheusProperties.java

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -101,6 +101,16 @@ public static class Pushgateway {
101101
*/
102102
private String baseUrl = "http://localhost:9091";
103103

104+
/**
105+
* Login user of the Prometheus Pushgateway.
106+
*/
107+
private String username;
108+
109+
/**
110+
* Login password of the Prometheus Pushgateway.
111+
*/
112+
private String password;
113+
104114
/**
105115
* Frequency with which to push metrics.
106116
*/
@@ -137,6 +147,22 @@ public void setBaseUrl(String baseUrl) {
137147
this.baseUrl = baseUrl;
138148
}
139149

150+
public String getUsername() {
151+
return this.username;
152+
}
153+
154+
public void setUsername(String username) {
155+
this.username = username;
156+
}
157+
158+
public String getPassword() {
159+
return this.password;
160+
}
161+
162+
public void setPassword(String password) {
163+
this.password = password;
164+
}
165+
140166
public Duration getPushRate() {
141167
return this.pushRate;
142168
}

spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/export/prometheus/PrometheusMetricsExportAutoConfigurationTests.java

Lines changed: 42 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,16 @@
1616

1717
package org.springframework.boot.actuate.autoconfigure.metrics.export.prometheus;
1818

19+
import java.util.function.Consumer;
20+
1921
import io.micrometer.core.instrument.Clock;
2022
import io.micrometer.prometheus.PrometheusConfig;
2123
import io.micrometer.prometheus.PrometheusMeterRegistry;
2224
import io.prometheus.client.CollectorRegistry;
25+
import io.prometheus.client.exporter.BasicAuthHttpConnectionFactory;
26+
import io.prometheus.client.exporter.DefaultHttpConnectionFactory;
27+
import io.prometheus.client.exporter.HttpConnectionFactory;
28+
import io.prometheus.client.exporter.PushGateway;
2329
import org.junit.jupiter.api.Test;
2430
import org.junit.jupiter.api.extension.ExtendWith;
2531

@@ -29,6 +35,7 @@
2935
import org.springframework.boot.autoconfigure.AutoConfigurations;
3036
import org.springframework.boot.test.context.assertj.AssertableApplicationContext;
3137
import org.springframework.boot.test.context.runner.ApplicationContextRunner;
38+
import org.springframework.boot.test.context.runner.ContextConsumer;
3239
import org.springframework.boot.test.system.CapturedOutput;
3340
import org.springframework.boot.test.system.OutputCaptureExtension;
3441
import org.springframework.context.annotation.Bean;
@@ -42,6 +49,7 @@
4249
* Tests for {@link PrometheusMetricsExportAutoConfiguration}.
4350
*
4451
* @author Andy Wilkinson
52+
* @author Stephane Nicoll
4553
*/
4654
@ExtendWith(OutputCaptureExtension.class)
4755
class PrometheusMetricsExportAutoConfigurationTests {
@@ -142,6 +150,15 @@ void withPushGatewayEnabled(CapturedOutput output) {
142150
});
143151
}
144152

153+
@Test
154+
void withPushGatewayNoBasicAuth() {
155+
this.contextRunner.withConfiguration(AutoConfigurations.of(ManagementContextAutoConfiguration.class))
156+
.withPropertyValues("management.metrics.export.prometheus.pushgateway.enabled=true")
157+
.withUserConfiguration(BaseConfiguration.class)
158+
.run(hasHttpConnectionFactory((httpConnectionFactory) -> assertThat(httpConnectionFactory)
159+
.isInstanceOf(DefaultHttpConnectionFactory.class)));
160+
}
161+
145162
@Test
146163
@Deprecated
147164
void withCustomLegacyPushGatewayURL(CapturedOutput output) {
@@ -163,11 +180,34 @@ void withCustomPushGatewayURL() {
163180
.run((context) -> hasGatewayURL(context, "https://example.com:8080/metrics/"));
164181
}
165182

183+
@Test
184+
void withPushGatewayBasicAuth() {
185+
this.contextRunner.withConfiguration(AutoConfigurations.of(ManagementContextAutoConfiguration.class))
186+
.withPropertyValues("management.metrics.export.prometheus.pushgateway.enabled=true",
187+
"management.metrics.export.prometheus.pushgateway.username=admin",
188+
"management.metrics.export.prometheus.pushgateway.password=secret")
189+
.withUserConfiguration(BaseConfiguration.class)
190+
.run(hasHttpConnectionFactory((httpConnectionFactory) -> assertThat(httpConnectionFactory)
191+
.isInstanceOf(BasicAuthHttpConnectionFactory.class)));
192+
}
193+
166194
private void hasGatewayURL(AssertableApplicationContext context, String url) {
195+
assertThat(getPushGateway(context)).hasFieldOrPropertyWithValue("gatewayBaseURL", url);
196+
}
197+
198+
private ContextConsumer<AssertableApplicationContext> hasHttpConnectionFactory(
199+
Consumer<HttpConnectionFactory> httpConnectionFactory) {
200+
return (context) -> {
201+
PushGateway pushGateway = getPushGateway(context);
202+
httpConnectionFactory
203+
.accept((HttpConnectionFactory) ReflectionTestUtils.getField(pushGateway, "connectionFactory"));
204+
};
205+
}
206+
207+
private PushGateway getPushGateway(AssertableApplicationContext context) {
167208
assertThat(context).hasSingleBean(PrometheusPushGatewayManager.class);
168209
PrometheusPushGatewayManager gatewayManager = context.getBean(PrometheusPushGatewayManager.class);
169-
Object pushGateway = ReflectionTestUtils.getField(gatewayManager, "pushGateway");
170-
assertThat(pushGateway).hasFieldOrPropertyWithValue("gatewayBaseURL", url);
210+
return (PushGateway) ReflectionTestUtils.getField(gatewayManager, "pushGateway");
171211
}
172212

173213
@Configuration(proxyBeanMethods = false)

0 commit comments

Comments
 (0)