diff --git a/src/Testcontainers/Builders/MTlsEndpointAuthenticationProvider.cs b/src/Testcontainers/Builders/MTlsEndpointAuthenticationProvider.cs
index 49a6edd0f..fba9356f2 100644
--- a/src/Testcontainers/Builders/MTlsEndpointAuthenticationProvider.cs
+++ b/src/Testcontainers/Builders/MTlsEndpointAuthenticationProvider.cs
@@ -27,7 +27,7 @@ internal sealed class MTlsEndpointAuthenticationProvider : DockerEndpointAuthent
private static readonly Regex PemData = new Regex("-----BEGIN (.*)-----(.*)-----END (.*)-----", RegexOptions.Multiline);
private readonly Uri dockerEngine;
- private readonly bool dockerTlsVerifyEnabled;
+ private readonly bool? dockerTlsVerifyEnabled;
private readonly string dockerCaCertFile;
private readonly string dockerClientCertFile;
private readonly string dockerClientKeyFile;
@@ -36,13 +36,15 @@ internal sealed class MTlsEndpointAuthenticationProvider : DockerEndpointAuthent
public MTlsEndpointAuthenticationProvider()
{
- var dockerHostValue = Environment.GetEnvironmentVariable("DOCKER_HOST");
- var dockerTlsVerifyValue = Environment.GetEnvironmentVariable("DOCKER_TLS_VERIFY");
- var dockerCertPathValue = Environment.GetEnvironmentVariable("DOCKER_CERT_PATH");
- var dockerCertPath = dockerCertPathValue ?? Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), DefaultCertPath);
+ ICustomConfiguration propertiesFileConfiguration = new PropertiesFileConfiguration();
+ ICustomConfiguration environmentConfiguration = new EnvironmentConfiguration();
- this.dockerEngine = Uri.TryCreate(dockerHostValue, UriKind.RelativeOrAbsolute, out var dockerHost) ? dockerHost : DefaultTlsDockerEndpoint;
- this.dockerTlsVerifyEnabled = int.TryParse(dockerTlsVerifyValue, out var dockerTlsVerify) && dockerTlsVerify == 1;
+ var dockerCertPath = propertiesFileConfiguration.GetDockerCertPath()
+ ?? environmentConfiguration.GetDockerCertPath()
+ ?? Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), DefaultCertPath);
+
+ this.dockerEngine = propertiesFileConfiguration.GetDockerHost() ?? environmentConfiguration.GetDockerHost() ?? DefaultTlsDockerEndpoint;
+ this.dockerTlsVerifyEnabled = propertiesFileConfiguration.GetDockerTlsVerify() ?? environmentConfiguration.GetDockerTlsVerify();
this.dockerCaCertFile = Path.Combine(dockerCertPath, DefaultCaCertFileName);
this.dockerClientCertFile = Path.Combine(dockerCertPath, DefaultClientCertFileName);
this.dockerClientKeyFile = Path.Combine(dockerCertPath, DefaultClientKeyFileName);
@@ -53,7 +55,7 @@ public MTlsEndpointAuthenticationProvider()
///
public override bool IsApplicable()
{
- return this.dockerTlsVerifyEnabled && File.Exists(this.dockerClientCertFile) && File.Exists(this.dockerClientKeyFile);
+ return this.dockerTlsVerifyEnabled.HasValue && this.dockerTlsVerifyEnabled.Value && File.Exists(this.dockerClientCertFile) && File.Exists(this.dockerClientKeyFile);
}
///
diff --git a/src/Testcontainers/Builders/TlsEndpointAuthenticationProvider.cs b/src/Testcontainers/Builders/TlsEndpointAuthenticationProvider.cs
index 6b8fabbed..6e576eedc 100644
--- a/src/Testcontainers/Builders/TlsEndpointAuthenticationProvider.cs
+++ b/src/Testcontainers/Builders/TlsEndpointAuthenticationProvider.cs
@@ -16,19 +16,21 @@ internal sealed class TlsEndpointAuthenticationProvider : DockerEndpointAuthenti
private static readonly Uri DefaultTlsDockerEndpoint = new Uri("tcp://localhost:2376");
private readonly Uri dockerEngine;
- private readonly bool dockerTlsEnabled;
+ private readonly bool? dockerTlsEnabled;
private readonly string dockerCaCertFile;
private readonly Lazy caCertificate;
public TlsEndpointAuthenticationProvider()
{
- var dockerHostValue = Environment.GetEnvironmentVariable("DOCKER_HOST");
- var dockerTlsValue = Environment.GetEnvironmentVariable("DOCKER_TLS");
- var dockerCertPathValue = Environment.GetEnvironmentVariable("DOCKER_CERT_PATH");
- var dockerCertPath = dockerCertPathValue ?? Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), DefaultCertPath);
+ ICustomConfiguration propertiesFileConfiguration = new PropertiesFileConfiguration();
+ ICustomConfiguration environmentConfiguration = new EnvironmentConfiguration();
- this.dockerEngine = Uri.TryCreate(dockerHostValue, UriKind.RelativeOrAbsolute, out var dockerHost) ? dockerHost : DefaultTlsDockerEndpoint;
- this.dockerTlsEnabled = int.TryParse(dockerTlsValue, out var dockerTls) && dockerTls == 1;
+ var dockerCertPath = propertiesFileConfiguration.GetDockerCertPath()
+ ?? environmentConfiguration.GetDockerCertPath()
+ ?? Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), DefaultCertPath);
+
+ this.dockerEngine = propertiesFileConfiguration.GetDockerHost() ?? environmentConfiguration.GetDockerHost() ?? DefaultTlsDockerEndpoint;
+ this.dockerTlsEnabled = propertiesFileConfiguration.GetDockerTls() ?? environmentConfiguration.GetDockerTls();
this.dockerCaCertFile = Path.Combine(dockerCertPath, DefaultCaCertFileName);
this.caCertificate = new Lazy(() => new X509Certificate2(this.dockerCaCertFile));
}
@@ -36,7 +38,7 @@ public TlsEndpointAuthenticationProvider()
///
public override bool IsApplicable()
{
- return this.dockerTlsEnabled;
+ return this.dockerTlsEnabled.HasValue && this.dockerTlsEnabled.Value;
}
///
diff --git a/src/Testcontainers/Configurations/CustomConfiguration.cs b/src/Testcontainers/Configurations/CustomConfiguration.cs
index 8c722a918..9eb7f649b 100644
--- a/src/Testcontainers/Configurations/CustomConfiguration.cs
+++ b/src/Testcontainers/Configurations/CustomConfiguration.cs
@@ -1,7 +1,8 @@
-namespace DotNet.Testcontainers.Configurations
+namespace DotNet.Testcontainers.Configurations
{
using System;
using System.Collections.Generic;
+ using System.Globalization;
using System.Text.Json;
using DotNet.Testcontainers.Images;
@@ -14,6 +15,37 @@ protected CustomConfiguration(IReadOnlyDictionary properties)
this.properties = properties;
}
+ protected JsonDocument GetDockerAuthConfig(string propertyName)
+ {
+ _ = this.properties.TryGetValue(propertyName, out var propertyValue);
+
+ if (string.IsNullOrEmpty(propertyValue))
+ {
+ return null;
+ }
+
+ try
+ {
+ return JsonDocument.Parse(propertyValue);
+ }
+ catch (Exception)
+ {
+ return null;
+ }
+ }
+
+ protected string GetDockerCertPath(string propertyName)
+ {
+ _ = this.properties.TryGetValue(propertyName, out var propertyValue);
+
+ if (string.IsNullOrWhiteSpace(propertyValue))
+ {
+ return null;
+ }
+
+ return propertyValue;
+ }
+
protected string GetDockerConfig(string propertyName)
{
_ = this.properties.TryGetValue(propertyName, out var propertyValue);
@@ -25,23 +57,38 @@ protected Uri GetDockerHost(string propertyName)
return this.properties.TryGetValue(propertyName, out var propertyValue) && Uri.TryCreate(propertyValue, UriKind.RelativeOrAbsolute, out var dockerHost) ? dockerHost : null;
}
- protected JsonDocument GetDockerAuthConfig(string propertyName)
+ protected bool? GetDockerTls(string propertyName)
{
- _ = this.properties.TryGetValue(propertyName, out var propertyValue);
-
- if (string.IsNullOrEmpty(propertyValue))
+ if (!this.properties.TryGetValue(propertyName, out var propertyValue) || string.IsNullOrWhiteSpace(propertyValue))
{
return null;
}
- try
+ propertyValue = propertyValue.Trim().ToLower(CultureInfo.InvariantCulture);
+
+ if (bool.TryParse(propertyValue, out var dockerTls))
{
- return JsonDocument.Parse(propertyValue);
+ return dockerTls;
}
- catch (Exception)
+
+ return propertyValue == "1";
+ }
+
+ protected bool? GetDockerTlsVerify(string propertyName)
+ {
+ if (!this.properties.TryGetValue(propertyName, out var propertyValue) || string.IsNullOrWhiteSpace(propertyValue))
{
return null;
}
+
+ propertyValue = propertyValue.Trim().ToLower(CultureInfo.InvariantCulture);
+
+ if (bool.TryParse(propertyValue, out var dockerTlsVerify))
+ {
+ return dockerTlsVerify;
+ }
+
+ return propertyValue == "1";
}
protected bool GetRyukDisabled(string propertyName)
diff --git a/src/Testcontainers/Configurations/EnvironmentConfiguration.cs b/src/Testcontainers/Configurations/EnvironmentConfiguration.cs
index d99b55926..12c80d1df 100644
--- a/src/Testcontainers/Configurations/EnvironmentConfiguration.cs
+++ b/src/Testcontainers/Configurations/EnvironmentConfiguration.cs
@@ -1,4 +1,4 @@
-namespace DotNet.Testcontainers.Configurations
+namespace DotNet.Testcontainers.Configurations
{
using System;
using System.Linq;
@@ -10,11 +10,17 @@
///
internal sealed class EnvironmentConfiguration : CustomConfiguration, ICustomConfiguration
{
+ private const string DockerAuthConfig = "DOCKER_AUTH_CONFIG";
+
+ private const string DockerCertPath = "DOCKER_CERT_PATH";
+
private const string DockerConfig = "DOCKER_CONFIG";
private const string DockerHost = "DOCKER_HOST";
- private const string DockerAuthConfig = "DOCKER_AUTH_CONFIG";
+ private const string DockerTls = "DOCKER_TLS";
+
+ private const string DockerTlsVerify = "DOCKER_TLS_VERIFY";
private const string RyukDisabled = "TESTCONTAINERS_RYUK_DISABLED";
@@ -30,7 +36,18 @@ static EnvironmentConfiguration()
/// Initializes a new instance of the class.
///
public EnvironmentConfiguration()
- : base(new[] { DockerConfig, DockerHost, DockerAuthConfig, RyukDisabled, RyukContainerImage, HubImageNamePrefix }
+ : base(new[]
+ {
+ DockerAuthConfig,
+ DockerCertPath,
+ DockerConfig,
+ DockerHost,
+ DockerTls,
+ DockerTlsVerify,
+ RyukDisabled,
+ RyukContainerImage,
+ HubImageNamePrefix,
+ }
.ToDictionary(key => key, Environment.GetEnvironmentVariable))
{
}
@@ -41,6 +58,18 @@ public EnvironmentConfiguration()
public static ICustomConfiguration Instance { get; }
= new EnvironmentConfiguration();
+ ///
+ public JsonDocument GetDockerAuthConfig()
+ {
+ return this.GetDockerAuthConfig(DockerAuthConfig);
+ }
+
+ ///
+ public string GetDockerCertPath()
+ {
+ return this.GetDockerCertPath(DockerCertPath);
+ }
+
///
public string GetDockerConfig()
{
@@ -54,9 +83,15 @@ public Uri GetDockerHost()
}
///
- public JsonDocument GetDockerAuthConfig()
+ public bool? GetDockerTls()
{
- return this.GetDockerAuthConfig(DockerAuthConfig);
+ return this.GetDockerTls(DockerTls);
+ }
+
+ ///
+ public bool? GetDockerTlsVerify()
+ {
+ return this.GetDockerTlsVerify(DockerTlsVerify);
}
///
diff --git a/src/Testcontainers/Configurations/ICustomConfiguration.cs b/src/Testcontainers/Configurations/ICustomConfiguration.cs
index 9256cb884..ef93fcb85 100644
--- a/src/Testcontainers/Configurations/ICustomConfiguration.cs
+++ b/src/Testcontainers/Configurations/ICustomConfiguration.cs
@@ -1,4 +1,4 @@
-namespace DotNet.Testcontainers.Configurations
+namespace DotNet.Testcontainers.Configurations
{
using System;
using System.Text.Json;
@@ -10,6 +10,22 @@
///
internal interface ICustomConfiguration
{
+ ///
+ /// Gets the Docker registry authentication custom configuration.
+ ///
+ /// The Docker authentication custom configuration.
+ /// https://docs.gitlab.com/ee/ci/docker/using_docker_images.html#access-an-image-from-a-private-container-registry.
+ [CanBeNull]
+ JsonDocument GetDockerAuthConfig();
+
+ ///
+ /// Gets the Docker location of your authentication keys and host certificate.
+ ///
+ /// The Docker location of your authentication keys and host certificate.
+ /// https://www.testcontainers.org/features/configuration/#customizing-docker-host-detection.
+ [CanBeNull]
+ string GetDockerCertPath();
+
///
/// Gets the Docker config custom configuration.
///
@@ -27,12 +43,18 @@ internal interface ICustomConfiguration
Uri GetDockerHost();
///
- /// Gets the Docker registry authentication custom configuration.
+ /// Gets the Docker uses TLS.
///
- /// The Docker authentication custom configuration.
- /// https://docs.gitlab.com/ee/ci/docker/using_docker_images.html#access-an-image-from-a-private-container-registry.
- [CanBeNull]
- JsonDocument GetDockerAuthConfig();
+ /// The Docker uses TLS.
+ /// https://www.testcontainers.org/features/configuration/#customizing-docker-host-detection.
+ bool? GetDockerTls();
+
+ ///
+ /// Gets the Docker uses TLS and verifies the remote.
+ ///
+ /// The Docker uses TLS and verifies the remote.
+ /// https://www.testcontainers.org/features/configuration/#customizing-docker-host-detection.
+ bool? GetDockerTlsVerify();
///
/// Gets the Ryuk disabled custom configuration.
diff --git a/src/Testcontainers/Configurations/PropertiesFileConfiguration.cs b/src/Testcontainers/Configurations/PropertiesFileConfiguration.cs
index 1548425f9..f4fed505c 100644
--- a/src/Testcontainers/Configurations/PropertiesFileConfiguration.cs
+++ b/src/Testcontainers/Configurations/PropertiesFileConfiguration.cs
@@ -1,4 +1,4 @@
-namespace DotNet.Testcontainers.Configurations
+namespace DotNet.Testcontainers.Configurations
{
using System;
using System.IO;
@@ -56,6 +56,20 @@ public PropertiesFileConfiguration(params string[] lines)
public static ICustomConfiguration Instance { get; }
= new PropertiesFileConfiguration();
+ ///
+ public JsonDocument GetDockerAuthConfig()
+ {
+ const string propertyName = "docker.auth.config";
+ return this.GetDockerAuthConfig(propertyName);
+ }
+
+ ///
+ public string GetDockerCertPath()
+ {
+ const string propertyName = "docker.cert.path";
+ return this.GetDockerCertPath(propertyName);
+ }
+
///
public string GetDockerConfig()
{
@@ -71,10 +85,17 @@ public Uri GetDockerHost()
}
///
- public JsonDocument GetDockerAuthConfig()
+ public bool? GetDockerTls()
{
- const string propertyName = "docker.auth.config";
- return this.GetDockerAuthConfig(propertyName);
+ const string propertyName = "docker.tls";
+ return this.GetDockerTls(propertyName);
+ }
+
+ ///
+ public bool? GetDockerTlsVerify()
+ {
+ const string propertyName = "docker.tls.verify";
+ return this.GetDockerTlsVerify(propertyName);
}
///
diff --git a/tests/Testcontainers.Tests/Unit/Configurations/CustomConfigurationTest.cs b/tests/Testcontainers.Tests/Unit/Configurations/CustomConfigurationTest.cs
index f4fd8f020..1730f1126 100644
--- a/tests/Testcontainers.Tests/Unit/Configurations/CustomConfigurationTest.cs
+++ b/tests/Testcontainers.Tests/Unit/Configurations/CustomConfigurationTest.cs
@@ -1,4 +1,4 @@
-namespace DotNet.Testcontainers.Tests.Unit
+namespace DotNet.Testcontainers.Tests.Unit
{
using System;
using System.Collections.Generic;
@@ -15,14 +15,43 @@ public sealed class EnvironmentConfigurationTest : IDisposable
static EnvironmentConfigurationTest()
{
+ EnvironmentVariables.Add("DOCKER_AUTH_CONFIG");
+ EnvironmentVariables.Add("DOCKER_CERT_PATH");
EnvironmentVariables.Add("DOCKER_CONFIG");
EnvironmentVariables.Add("DOCKER_HOST");
- EnvironmentVariables.Add("DOCKER_AUTH_CONFIG");
+ EnvironmentVariables.Add("DOCKER_TLS");
+ EnvironmentVariables.Add("DOCKER_TLS_VERIFY");
EnvironmentVariables.Add("TESTCONTAINERS_RYUK_DISABLED");
EnvironmentVariables.Add("TESTCONTAINERS_RYUK_CONTAINER_IMAGE");
EnvironmentVariables.Add("TESTCONTAINERS_HUB_IMAGE_NAME_PREFIX");
}
+ [Theory]
+ [InlineData("", "", null)]
+ [InlineData("DOCKER_AUTH_CONFIG", "", null)]
+ [InlineData("DOCKER_AUTH_CONFIG", "{jsonReaderException}", null)]
+ [InlineData("DOCKER_AUTH_CONFIG", "{}", "{}")]
+ [InlineData("DOCKER_AUTH_CONFIG", "{\"auths\":null}", "{\"auths\":null}")]
+ [InlineData("DOCKER_AUTH_CONFIG", "{\"auths\":{}}", "{\"auths\":{}}")]
+ [InlineData("DOCKER_AUTH_CONFIG", "{\"auths\":{\"ghcr.io\":{}}}", "{\"auths\":{\"ghcr.io\":{}}}")]
+ public void GetDockerAuthConfigCustomConfiguration(string propertyName, string propertyValue, string expected)
+ {
+ SetEnvironmentVariable(propertyName, propertyValue);
+ ICustomConfiguration customConfiguration = new EnvironmentConfiguration();
+ Assert.Equal(expected, customConfiguration.GetDockerAuthConfig()?.RootElement.ToString());
+ }
+
+ [Theory]
+ [InlineData("", "", null)]
+ [InlineData("DOCKER_CERT_PATH", "", null)]
+ [InlineData("DOCKER_CERT_PATH", "/home/docker/.docker/certs", "/home/docker/.docker/certs")]
+ public void GetDockerCertPathCustomConfiguration(string propertyName, string propertyValue, string expected)
+ {
+ SetEnvironmentVariable(propertyName, propertyValue);
+ ICustomConfiguration customConfiguration = new EnvironmentConfiguration();
+ Assert.Equal(expected, customConfiguration.GetDockerCertPath());
+ }
+
[Theory]
[InlineData("", "", null)]
[InlineData("DOCKER_CONFIG", "", null)]
@@ -47,17 +76,34 @@ public void GetDockerHostCustomConfiguration(string propertyName, string propert
[Theory]
[InlineData("", "", null)]
- [InlineData("DOCKER_AUTH_CONFIG", "", null)]
- [InlineData("DOCKER_AUTH_CONFIG", "{jsonReaderException}", null)]
- [InlineData("DOCKER_AUTH_CONFIG", "{}", "{}")]
- [InlineData("DOCKER_AUTH_CONFIG", "{\"auths\":null}", "{\"auths\":null}")]
- [InlineData("DOCKER_AUTH_CONFIG", "{\"auths\":{}}", "{\"auths\":{}}")]
- [InlineData("DOCKER_AUTH_CONFIG", "{\"auths\":{\"ghcr.io\":{}}}", "{\"auths\":{\"ghcr.io\":{}}}")]
- public void GetDockerAuthConfigCustomConfiguration(string propertyName, string propertyValue, string expected)
+ [InlineData("DOCKER_TLS", "", null)]
+ [InlineData("DOCKER_TLS", "0", false)]
+ [InlineData("DOCKER_TLS", "false", false)]
+ [InlineData("DOCKER_TLS", "FALSE", false)]
+ [InlineData("DOCKER_TLS", "1", true)]
+ [InlineData("DOCKER_TLS", "TRUE", true)]
+ [InlineData("DOCKER_TLS", "true", true)]
+ public void GetDockerTlsCustomConfiguration(string propertyName, string propertyValue, bool? expected)
{
SetEnvironmentVariable(propertyName, propertyValue);
ICustomConfiguration customConfiguration = new EnvironmentConfiguration();
- Assert.Equal(expected, customConfiguration.GetDockerAuthConfig()?.RootElement.ToString());
+ Assert.Equal(expected, customConfiguration.GetDockerTls());
+ }
+
+ [Theory]
+ [InlineData("", "", null)]
+ [InlineData("DOCKER_TLS_VERIFY", "", null)]
+ [InlineData("DOCKER_TLS_VERIFY", "0", false)]
+ [InlineData("DOCKER_TLS_VERIFY", "false", false)]
+ [InlineData("DOCKER_TLS_VERIFY", "FALSE", false)]
+ [InlineData("DOCKER_TLS_VERIFY", "1", true)]
+ [InlineData("DOCKER_TLS_VERIFY", "TRUE", true)]
+ [InlineData("DOCKER_TLS_VERIFY", "true", true)]
+ public void GetDockerTlsVerifyCustomConfiguration(string propertyName, string propertyValue, bool? expected)
+ {
+ SetEnvironmentVariable(propertyName, propertyValue);
+ ICustomConfiguration customConfiguration = new EnvironmentConfiguration();
+ Assert.Equal(expected, customConfiguration.GetDockerTlsVerify());
}
[Theory]
@@ -147,6 +193,46 @@ public void GetDockerAuthConfigCustomConfiguration(string configuration, string
Assert.Equal(expected, customConfiguration.GetDockerAuthConfig()?.RootElement.ToString());
}
+ [Theory]
+ [InlineData("", null)]
+ [InlineData("docker.tls=", null)]
+ [InlineData("docker.tls=0", false)]
+ [InlineData("docker.tls=false", false)]
+ [InlineData("docker.tls=FALSE", false)]
+ [InlineData("docker.tls=1", true)]
+ [InlineData("docker.tls=TRUE", true)]
+ [InlineData("docker.tls=true", true)]
+ public void GetDockerTlsCustomConfiguration(string configuration, bool? expected)
+ {
+ ICustomConfiguration customConfiguration = new PropertiesFileConfiguration(new[] { configuration });
+ Assert.Equal(expected, customConfiguration.GetDockerTls());
+ }
+
+ [Theory]
+ [InlineData("", null)]
+ [InlineData("docker.tls.verify=", null)]
+ [InlineData("docker.tls.verify=0", false)]
+ [InlineData("docker.tls.verify=false", false)]
+ [InlineData("docker.tls.verify=FALSE", false)]
+ [InlineData("docker.tls.verify=1", true)]
+ [InlineData("docker.tls.verify=TRUE", true)]
+ [InlineData("docker.tls.verify=true", true)]
+ public void GetDockerTlsVerifyCustomConfiguration(string configuration, bool? expected)
+ {
+ ICustomConfiguration customConfiguration = new PropertiesFileConfiguration(new[] { configuration });
+ Assert.Equal(expected, customConfiguration.GetDockerTlsVerify());
+ }
+
+ [Theory]
+ [InlineData("", null)]
+ [InlineData("docker.cert.path=", null)]
+ [InlineData("docker.cert.path=/home/docker/.docker/certs", "/home/docker/.docker/certs")]
+ public void GetDockerCertPathCustomConfiguration(string configuration, string expected)
+ {
+ ICustomConfiguration customConfiguration = new PropertiesFileConfiguration(new[] { configuration });
+ Assert.Equal(expected, customConfiguration.GetDockerCertPath());
+ }
+
[Theory]
[InlineData("", false)]
[InlineData("ryuk.disabled=", false)]