Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/release/1.0.2.0'
Browse files Browse the repository at this point in the history
* origin/release/1.0.2.0:
  release 1.0.2.0
  update dependencies
  add proxy password with *** to debug log if set
  adds comment why preemptive authorization header is needed
  rename method to encodeCredentials
  use oauth2 instead of only oauth
  change log level for coinfuguration when using proxy to debug
  add logging for proxy
  rename buffer to include length
  fix typo
  check for proxy variables before setting authentication
  remove indirection via constants, more precise comments for preemptive authoization headers
  enable proxy auth for java.net.HttpClient
  replace strings with constants
  use TLS context, fox typo
  log configuration of oauth provider, throw exception if token could not be retrieved
  client credentials workflow implementation
  publish artefact on release
  remove not needed whitespace
  start new development cylve and fix mvn action for publish
  • Loading branch information
wetret committed Aug 1, 2024
2 parents 4ce4d86 + 670853e commit 26001a2
Show file tree
Hide file tree
Showing 10 changed files with 418 additions and 28 deletions.
7 changes: 5 additions & 2 deletions .github/workflows/maven-publish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,15 @@ on:
pull_request:
types: [closed]
branches: [develop]
release:
types: [published]

jobs:
publish:

# Only run if pull requests are merged, omit running if pull requests are closed without merging
if: github.event.pull_request.merged
# Only run if releases are published or pull requests are merged,
# omit running if pull requests are closed without merging
if: github.event.pull_request.merged || github.event.action == 'published'

runs-on: ubuntu-latest

Expand Down
24 changes: 12 additions & 12 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

<groupId>de.medizininformatik-initiative</groupId>
<artifactId>mii-processes-common</artifactId>
<version>1.0.1.0</version>
<version>1.0.2.0</version>

<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
Expand Down Expand Up @@ -39,7 +39,7 @@
<dependency>
<groupId>dev.dsf</groupId>
<artifactId>dsf-bpe-process-api-v1</artifactId>
<version>1.5.1</version>
<version>1.5.2</version>
<scope>provided</scope>
</dependency>
<dependency>
Expand Down Expand Up @@ -87,12 +87,12 @@
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>3.2.5</version>
<version>3.3.1</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<version>3.4.1</version>
<version>3.4.2</version>
<configuration>
<archive>
<manifest>
Expand All @@ -109,7 +109,7 @@
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>3.5.3</version>
<version>3.6.0</version>
<executions>
<execution>
<phase>package</phase>
Expand Down Expand Up @@ -144,12 +144,12 @@
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>3.6.1</version>
<version>3.7.1</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-clean-plugin</artifactId>
<version>3.3.2</version>
<version>3.4.0</version>
</plugin>
<plugin>
<groupId>org.codehaus.mojo</groupId>
Expand All @@ -172,15 +172,15 @@
<plugin>
<groupId>net.revelc.code.formatter</groupId>
<artifactId>formatter-maven-plugin</artifactId>
<version>2.23.0</version>
<version>2.24.1</version>
<configuration>
<configFile>eclipse-formatter-config.xml</configFile>
</configuration>
</plugin>
<plugin>
<groupId>net.revelc.code</groupId>
<artifactId>impsort-maven-plugin</artifactId>
<version>1.9.0</version>
<version>1.11.0</version>
<configuration>
<compliance>17</compliance>
<groups>java.,javax.,org.,com.</groups>
Expand All @@ -195,17 +195,17 @@
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-project-info-reports-plugin</artifactId>
<version>3.5.0</version>
<version>3.6.2</version>
</plugin>
<plugin>
<groupId>com.github.spotbugs</groupId>
<artifactId>spotbugs-maven-plugin</artifactId>
<version>4.8.5.0</version>
<version>4.8.6.2</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-pmd-plugin</artifactId>
<version>3.22.0</version>
<version>3.24.0</version>
</plugin>
</plugins>
</build>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@

import ca.uhn.fhir.context.FhirContext;
import de.medizininformatik_initiative.processes.common.fhir.client.logging.DataLogger;
import de.medizininformatik_initiative.processes.common.fhir.client.token.TokenProvider;
import de.rwh.utils.crypto.CertificateHelper;
import de.rwh.utils.crypto.io.CertificateReader;
import de.rwh.utils.crypto.io.PemIo;
Expand All @@ -38,6 +39,7 @@ public class FhirClientFactory
private final String fhirServerBasicAuthUsername;
private final String fhirServerBasicAuthPassword;
private final String fhirServerBearerToken;
private final TokenProvider fhirServerOAuth2TokenProvider;

private final String proxyUrl;
private final String proxyUsername;
Expand All @@ -54,8 +56,8 @@ public class FhirClientFactory
public FhirClientFactory(Path trustStorePath, Path certificatePath, Path privateKeyPath, char[] privateKeyPassword,
int connectTimeout, int socketTimeout, int connectionRequestTimeout, String fhirServerBase,
String fhirServerBasicAuthUsername, String fhirServerBasicAuthPassword, String fhirServerBearerToken,
String proxyUrl, String proxyUsername, String proxyPassword, boolean hapiClientVerbose,
FhirContext fhirContext, String localIdentifierValue, DataLogger dataLogger)
TokenProvider fhirServerOAuth2TokenProvider, String proxyUrl, String proxyUsername, String proxyPassword,
boolean hapiClientVerbose, FhirContext fhirContext, String localIdentifierValue, DataLogger dataLogger)
{
this.trustStorePath = trustStorePath;
this.certificatePath = certificatePath;
Expand All @@ -70,6 +72,7 @@ public FhirClientFactory(Path trustStorePath, Path certificatePath, Path private
this.fhirServerBasicAuthUsername = fhirServerBasicAuthUsername;
this.fhirServerBasicAuthPassword = fhirServerBasicAuthPassword;
this.fhirServerBearerToken = fhirServerBearerToken;
this.fhirServerOAuth2TokenProvider = fhirServerOAuth2TokenProvider;

this.proxyUrl = proxyUrl;
this.proxyUsername = proxyUsername;
Expand All @@ -89,11 +92,12 @@ public void testConnection()
{
logger.info(
"Testing connection to FHIR server with {trustStorePath: {}, certificatePath: {}, privateKeyPath: {}, privateKeyPassword: {},"
+ " basicAuthUsername {}, basicAuthPassword {}, bearerToken {}, serverBase: {}, proxyUrl {}, proxyUsername {}, proxyPassword {}}",
+ " basicAuthUsername: {}, basicAuthPassword: {}, bearerToken: {}, oauth2Provider: {}, serverBase: {}, proxyUrl: {}, proxyUsername: {}, proxyPassword: {}}",
trustStorePath, certificatePath, privateKeyPath, privateKeyPassword != null ? "***" : "null",
fhirServerBasicAuthUsername, fhirServerBasicAuthPassword != null ? "***" : "null",
fhirServerBearerToken != null ? "***" : "null", fhirServerBase, proxyUrl, proxyUsername,
proxyPassword != null ? "***" : "null");
fhirServerBearerToken != null ? "***" : "null",
fhirServerOAuth2TokenProvider != null ? fhirServerOAuth2TokenProvider.getInfo() : "null",
fhirServerBase, proxyUrl, proxyUsername, proxyPassword != null ? "***" : "null");

getFhirClient().testConnection();
}
Expand Down Expand Up @@ -137,8 +141,8 @@ protected FhirClient createFhirClientImpl()

return new FhirClientImpl(trustStore, keyStore, keyStorePassword, connectTimeout, socketTimeout,
connectionRequestTimeout, fhirServerBasicAuthUsername, fhirServerBasicAuthPassword,
fhirServerBearerToken, fhirServerBase, proxyUrl, proxyUsername, proxyPassword, hapiClientVerbose,
fhirContext, localIdentifierValue, dataLogger);
fhirServerBearerToken, fhirServerOAuth2TokenProvider, fhirServerBase, proxyUrl, proxyUsername,
proxyPassword, hapiClientVerbose, fhirContext, localIdentifierValue, dataLogger);
}

private KeyStore readTrustStore(Path trustPath)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,10 @@
import ca.uhn.fhir.rest.client.interceptor.BearerTokenAuthInterceptor;
import ca.uhn.fhir.rest.client.interceptor.LoggingInterceptor;
import ca.uhn.fhir.rest.gclient.IReadTyped;
import de.medizininformatik_initiative.processes.common.fhir.client.interceptor.OAuth2Interceptor;
import de.medizininformatik_initiative.processes.common.fhir.client.logging.DataLogger;
import de.medizininformatik_initiative.processes.common.fhir.client.logging.HapiClientLogger;
import de.medizininformatik_initiative.processes.common.fhir.client.token.TokenProvider;

public class FhirClientImpl implements FhirClient
{
Expand All @@ -39,6 +41,7 @@ public class FhirClientImpl implements FhirClient
private final String fhirServerBasicAuthUsername;
private final String fhirServerBasicAuthPassword;
private final String fhirServerBearerToken;
private final TokenProvider fhirServerOAuth2TokenProvider;

private final boolean hapiClientVerbose;

Expand All @@ -50,9 +53,10 @@ public class FhirClientImpl implements FhirClient

public FhirClientImpl(KeyStore trustStore, KeyStore keyStore, char[] keyStorePassword, int connectTimeout,
int socketTimeout, int connectionRequestTimeout, String fhirServerBasicAuthUsername,
String fhirServerBasicAuthPassword, String fhirServerBearerToken, String fhirServerBase, String proxyUrl,
String proxyUsername, String proxyPassword, boolean hapiClientVerbose, FhirContext fhirContext,
String localIdentifierValue, DataLogger dataLogger)
String fhirServerBasicAuthPassword, String fhirServerBearerToken,
TokenProvider fhirServerOAuth2TokenProvider, String fhirServerBase, String proxyUrl, String proxyUsername,
String proxyPassword, boolean hapiClientVerbose, FhirContext fhirContext, String localIdentifierValue,
DataLogger dataLogger)
{
clientFactory = createClientFactory(trustStore, keyStore, keyStorePassword, connectTimeout, socketTimeout,
connectionRequestTimeout);
Expand All @@ -62,6 +66,7 @@ public FhirClientImpl(KeyStore trustStore, KeyStore keyStore, char[] keyStorePas
this.fhirServerBasicAuthUsername = fhirServerBasicAuthUsername;
this.fhirServerBasicAuthPassword = fhirServerBasicAuthPassword;
this.fhirServerBearerToken = fhirServerBearerToken;
this.fhirServerOAuth2TokenProvider = fhirServerOAuth2TokenProvider;

configureProxy(clientFactory, proxyUrl, proxyUsername, proxyPassword);

Expand All @@ -85,8 +90,9 @@ private void configureProxy(IRestfulClientFactory clientFactory, String proxyUrl
clientFactory.setProxy(url.getHost(), url.getPort());
clientFactory.setProxyCredentials(proxyUsername, proxyPassword);

logger.info("Using proxy for FHIR server connection with {host: {}, port: {}, username: {}}",
url.getHost(), url.getPort(), proxyUsername);
logger.debug(
"Using proxy for FHIR server connection with {host: {}, port: {}, username: {}, password: {}}",
url.getHost(), url.getPort(), proxyUsername, proxyPassword != null ? "***" : "null");
}
catch (MalformedURLException e)
{
Expand Down Expand Up @@ -118,12 +124,18 @@ private void configuredWithBasicAuth(IGenericClient client)
new BasicAuthInterceptor(fhirServerBasicAuthUsername, fhirServerBasicAuthPassword));
}

private void configureBearerTokenAuthInterceptor(IGenericClient client)
private void configuredWithBearerTokenAuth(IGenericClient client)
{
if (fhirServerBearerToken != null)
client.registerInterceptor(new BearerTokenAuthInterceptor(fhirServerBearerToken));
}

private void configuredWithOAuth2(IGenericClient client)
{
if (fhirServerOAuth2TokenProvider != null && fhirServerOAuth2TokenProvider.isConfigured())
client.registerInterceptor(new OAuth2Interceptor(fhirServerOAuth2TokenProvider));
}

private void configureLoggingInterceptor(IGenericClient client)
{
if (hapiClientVerbose)
Expand Down Expand Up @@ -158,7 +170,8 @@ public IGenericClient getGenericFhirClient()
IGenericClient client = clientFactory.newGenericClient(fhirServerBase);

configuredWithBasicAuth(client);
configureBearerTokenAuthInterceptor(client);
configuredWithBearerTokenAuth(client);
configuredWithOAuth2(client);
configureLoggingInterceptor(client);

return client;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
package de.medizininformatik_initiative.processes.common.fhir.client.interceptor;

import java.util.Objects;

import org.springframework.beans.factory.InitializingBean;

import ca.uhn.fhir.rest.api.Constants;
import ca.uhn.fhir.rest.client.api.IClientInterceptor;
import ca.uhn.fhir.rest.client.api.IHttpRequest;
import ca.uhn.fhir.rest.client.api.IHttpResponse;
import de.medizininformatik_initiative.processes.common.fhir.client.token.TokenProvider;

public class OAuth2Interceptor implements IClientInterceptor, InitializingBean
{
private final TokenProvider tokenProvider;

public OAuth2Interceptor(TokenProvider tokenProvider)
{
this.tokenProvider = tokenProvider;
}

@Override
public void afterPropertiesSet()
{
Objects.requireNonNull(tokenProvider, "tokenProvider");
}

@Override
public void interceptRequest(IHttpRequest theRequest)
{
theRequest.addHeader(Constants.HEADER_AUTHORIZATION,
Constants.HEADER_AUTHORIZATION_VALPREFIX_BEARER + tokenProvider.getToken());
}

@Override
public void interceptResponse(IHttpResponse theResponse)
{
// do not intercept response
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
package de.medizininformatik_initiative.processes.common.fhir.client.token;

import java.time.LocalDateTime;

import com.fasterxml.jackson.annotation.JsonCreator;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.JsonProperty;

@JsonIgnoreProperties(ignoreUnknown = true)
public class AccessToken
{
private static final int BUFFER_10 = 10;

private final String token;

private final LocalDateTime expiresAt;

@JsonCreator
public AccessToken(@JsonProperty("access_token") String token, @JsonProperty("expires_in") int expiresIn)
{
this.token = token;
this.expiresAt = LocalDateTime.now().plusSeconds(expiresIn);
}

public String get()
{
return token;
}

public boolean isExpired()
{
return LocalDateTime.now().plusSeconds(BUFFER_10).isAfter(expiresAt);
}
}
Loading

0 comments on commit 26001a2

Please sign in to comment.