Skip to content

Commit 08dede8

Browse files
committed
Added: Human Readable Bridgehead for frontend dto
1 parent f50c436 commit 08dede8

File tree

6 files changed

+138
-4
lines changed

6 files changed

+138
-4
lines changed

CHANGELOG.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ All notable changes to this project will be documented in this file.
44
The format is based on [Keep a Changelog](http://keepachangelog.com/)
55
and this project adheres to [Semantic Versioning](http://semver.org/).
66

7-
## [0.0.1 - 2024-11-06]
7+
## [0.0.1 - 2024-11-08]
88
### Added
99
- First version of the project
1010
- Spring Application
@@ -147,3 +147,4 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
147147
- Log bridgeheads sorted
148148
- Replace hyphen in frontend sites
149149
- Human Readable Bridgehead for frontend dto
150+
- Http proxy

src/main/java/de/samply/app/ProjectManagerConst.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -233,6 +233,8 @@ public class ProjectManagerConst {
233233
public final static String JWKS_URI_PROPERTY = "spring.security.oauth2.client.provider.oidc.jwk-set-uri";
234234
public final static String REGISTERED_BRIDGEHEADS = "bridgeheads";
235235
public final static String FRONTEND_CONFIG = "frontend";
236+
public final static String HTTP_PROXY_PREFIX = "http.proxy";
237+
public final static String HTTPS_PROXY_PREFIX = "https.proxy";
236238

237239
// Exporter
238240
public final static String SECURITY_ENABLED = "SECURITY_ENABLED";
@@ -461,6 +463,8 @@ public class ProjectManagerConst {
461463
public final static String CUSTOM_PROJECT_CONFIGURATION = "CUSTOM";
462464
public final static String EMAIL_SERVICE = "EMAIL_SERVICE";
463465
public final static String HYPHEN = "minus";
466+
public final static String HTTP_PROTOCOL_SCHEMA = "http";
467+
public final static String HTTPS_PROTOCOL_SCHEMA = "https";
464468

465469

466470
}
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
package de.samply.proxy;
2+
3+
import de.samply.app.ProjectManagerConst;
4+
import org.springframework.boot.context.properties.ConfigurationProperties;
5+
import org.springframework.stereotype.Component;
6+
7+
@Component
8+
@ConfigurationProperties(prefix = ProjectManagerConst.HTTP_PROXY_PREFIX)
9+
public class HttpProxyConfiguration extends ProxyConfiguration {
10+
11+
public HttpProxyConfiguration() {
12+
this.setSchema(ProjectManagerConst.HTTP_PROTOCOL_SCHEMA);
13+
}
14+
15+
}
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
package de.samply.proxy;
2+
3+
import de.samply.app.ProjectManagerConst;
4+
import org.springframework.boot.context.properties.ConfigurationProperties;
5+
import org.springframework.stereotype.Component;
6+
7+
@Component
8+
@ConfigurationProperties(prefix = ProjectManagerConst.HTTPS_PROXY_PREFIX)
9+
public class HttpsProxyConfiguration extends ProxyConfiguration {
10+
11+
public HttpsProxyConfiguration() {
12+
this.setSchema(ProjectManagerConst.HTTPS_PROTOCOL_SCHEMA);
13+
}
14+
15+
}
Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
package de.samply.proxy;
2+
3+
import jakarta.annotation.PostConstruct;
4+
import lombok.Data;
5+
import lombok.extern.slf4j.Slf4j;
6+
import org.springframework.util.StringUtils;
7+
8+
import java.net.MalformedURLException;
9+
import java.net.URL;
10+
import java.util.Arrays;
11+
import java.util.List;
12+
13+
@Slf4j
14+
@Data
15+
public class ProxyConfiguration {
16+
17+
private String host;
18+
private Integer port;
19+
private String schema;
20+
private String username;
21+
private String password;
22+
private String url;
23+
24+
// Comma-separated list of hosts or IPs to bypass the proxy
25+
private String noProxy;
26+
27+
// Convenience method to get noProxy as a List
28+
public List<String> getNoProxyList() {
29+
return noProxy != null ? Arrays.asList(noProxy.split(",")) : List.of();
30+
}
31+
32+
@PostConstruct
33+
public void init() throws MalformedURLException {
34+
if (StringUtils.hasText(this.url)) {
35+
URL url = new URL(this.url);
36+
this.schema = url.getProtocol();
37+
this.host = url.getHost();
38+
this.port = url.getPort();
39+
setProxyUserAndPassword(url.getUserInfo());
40+
}
41+
if (isConfigured()) {
42+
String schema = (this.schema != null) ? this.schema : "";
43+
log.info(schema + " Proxy configured:");
44+
log.info("\t-Host: " + this.host);
45+
log.info("\t-Port: " + this.port);
46+
if (username != null && password != null) {
47+
log.info("\t-Username: " + username);
48+
}
49+
}
50+
}
51+
52+
private void setProxyUserAndPassword(String userInfo) {
53+
if (userInfo != null) {
54+
String[] credentials = userInfo.split(":");
55+
if (credentials.length == 2) {
56+
this.username = credentials[0];
57+
this.password = credentials[1];
58+
}
59+
}
60+
}
61+
62+
public boolean isConfigured() {
63+
return StringUtils.hasText(this.host) && this.port != null;
64+
}
65+
66+
}

src/main/java/de/samply/utils/WebClientFactory.java

Lines changed: 36 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,20 @@
11
package de.samply.utils;
22

33
import de.samply.app.ProjectManagerConst;
4+
import de.samply.proxy.HttpProxyConfiguration;
5+
import de.samply.proxy.HttpsProxyConfiguration;
6+
import de.samply.proxy.ProxyConfiguration;
47
import io.netty.channel.ChannelOption;
58
import io.netty.channel.epoll.EpollChannelOption;
69
import org.springframework.beans.factory.annotation.Value;
710
import org.springframework.http.client.reactive.ReactorClientHttpConnector;
811
import org.springframework.stereotype.Component;
912
import org.springframework.web.reactive.function.client.WebClient;
1013
import reactor.netty.http.client.HttpClient;
14+
import reactor.netty.transport.ProxyProvider;
1115

1216
import java.time.Duration;
17+
import java.util.Optional;
1318

1419
@Component
1520
public class WebClientFactory {
@@ -22,6 +27,8 @@ public class WebClientFactory {
2227
private final int webClientTcpKeepIntervalInSeconds;
2328
private final int webClientTcpKeepConnetionNumberOfTries;
2429
private final int webClientBufferSizeInBytes;
30+
private Optional<ProxyConfiguration> httpProxyConfiguration = Optional.empty();
31+
private Optional<ProxyConfiguration> httpsProxyConfiguration = Optional.empty();
2532

2633
public WebClientFactory(
2734
@Value(ProjectManagerConst.WEBCLIENT_REQUEST_TIMEOUT_IN_SECONDS_SV) Integer webClientRequestTimeoutInSeconds,
@@ -31,7 +38,9 @@ public WebClientFactory(
3138
@Value(ProjectManagerConst.WEBCLIENT_TCP_KEEP_CONNECTION_NUMBER_OF_TRIES_SV) Integer webClientTcpKeepConnetionNumberOfTries,
3239
@Value(ProjectManagerConst.WEBCLIENT_MAX_NUMBER_OF_RETRIES_SV) Integer webClientMaxNumberOfRetries,
3340
@Value(ProjectManagerConst.WEBCLIENT_TIME_IN_SECONDS_AFTER_RETRY_WITH_FAILURE_SV) Integer webClientTimeInSecondsAfterRetryWithFailure,
34-
@Value(ProjectManagerConst.WEBCLIENT_BUFFER_SIZE_IN_BYTES_SV) Integer webClientBufferSizeInBytes
41+
@Value(ProjectManagerConst.WEBCLIENT_BUFFER_SIZE_IN_BYTES_SV) Integer webClientBufferSizeInBytes,
42+
HttpProxyConfiguration httpProxyConfiguration,
43+
HttpsProxyConfiguration httpsProxyConfiguration
3544
) {
3645
this.webClientMaxNumberOfRetries = webClientMaxNumberOfRetries;
3746
this.webClientTimeInSecondsAfterRetryWithFailure = webClientTimeInSecondsAfterRetryWithFailure;
@@ -41,10 +50,21 @@ public WebClientFactory(
4150
this.webClientTcpKeepIntervalInSeconds = webClientTcpKeepIntervalInSeconds;
4251
this.webClientTcpKeepConnetionNumberOfTries = webClientTcpKeepConnetionNumberOfTries;
4352
this.webClientBufferSizeInBytes = webClientBufferSizeInBytes;
53+
54+
setHttpProxies(httpProxyConfiguration, httpsProxyConfiguration);
55+
}
56+
57+
private void setHttpProxies(HttpProxyConfiguration httpProxyConfiguration, HttpsProxyConfiguration httpsProxyConfiguration) {
58+
if (httpProxyConfiguration.isConfigured()) {
59+
this.httpProxyConfiguration = Optional.of(httpProxyConfiguration);
60+
}
61+
if (httpsProxyConfiguration.isConfigured()) {
62+
this.httpsProxyConfiguration = Optional.of(httpsProxyConfiguration);
63+
}
4464
}
4565

4666
public WebClient createWebClient(String baseUrl) {
47-
return WebClient.builder()
67+
WebClient.Builder webClientBuilder = WebClient.builder()
4868
.codecs(codecs -> codecs.defaultCodecs().maxInMemorySize(webClientBufferSizeInBytes))
4969
.clientConnector(new ReactorClientHttpConnector(
5070
HttpClient.create()
@@ -55,9 +75,22 @@ public WebClient createWebClient(String baseUrl) {
5575
.option(EpollChannelOption.TCP_KEEPINTVL, webClientTcpKeepIntervalInSeconds)
5676
.option(EpollChannelOption.TCP_KEEPCNT, webClientTcpKeepConnetionNumberOfTries)
5777
))
58-
.baseUrl(baseUrl).build();
78+
.baseUrl(baseUrl);
79+
httpsProxyConfiguration.ifPresent(proxyConfig -> addProxy(webClientBuilder, proxyConfig));
80+
httpProxyConfiguration.ifPresent(proxyConfig -> addProxy(webClientBuilder, proxyConfig));
81+
return webClientBuilder.build();
5982
}
6083

84+
private void addProxy(WebClient.Builder webClientBuilder, ProxyConfiguration proxyConfiguration) {
85+
webClientBuilder.clientConnector(new ReactorClientHttpConnector(HttpClient.create()
86+
.proxy(proxy -> proxy.type(ProxyProvider.Proxy.HTTP)
87+
.host(proxyConfiguration.getHost())
88+
.port(proxyConfiguration.getPort())
89+
.username(proxyConfiguration.getUsername())
90+
.password(password -> proxyConfiguration.getPassword()) // Use Function.identity() here if needed
91+
.nonProxyHosts(proxyConfiguration.getNoProxy())
92+
)));
93+
}
6194

6295
public int getWebClientMaxNumberOfRetries() {
6396
return webClientMaxNumberOfRetries;

0 commit comments

Comments
 (0)