diff --git a/src/Akka.Bootstrap.Docker.Sample/Akka.Bootstrap.Docker.Sample.csproj b/src/Akka.Bootstrap.Docker.Sample/Akka.Bootstrap.Docker.Sample.csproj
index b16e9c6..f9f950a 100644
--- a/src/Akka.Bootstrap.Docker.Sample/Akka.Bootstrap.Docker.Sample.csproj
+++ b/src/Akka.Bootstrap.Docker.Sample/Akka.Bootstrap.Docker.Sample.csproj
@@ -14,8 +14,8 @@
-
-
+
+
diff --git a/src/Akka.Bootstrap.Docker.Sample/Program.cs b/src/Akka.Bootstrap.Docker.Sample/Program.cs
index e5c7355..73fa763 100644
--- a/src/Akka.Bootstrap.Docker.Sample/Program.cs
+++ b/src/Akka.Bootstrap.Docker.Sample/Program.cs
@@ -5,6 +5,7 @@
using Akka.Configuration;
using Akka.Event;
using Akka.Routing;
+using Hocon;
using Petabridge.Cmd.Cluster;
using Petabridge.Cmd.Host;
using Petabridge.Cmd.Remote;
@@ -20,7 +21,7 @@ static void Main(string[] args)
Environment.SetEnvironmentVariable("CLUSTER_IP", "localhost");
}
- var config = ConfigurationFactory.ParseString(File.ReadAllText("app.conf"))
+ var config = HoconConfigurationFactory.Default()
.BootstrapFromDocker(); // forces all Docker environment variable substitution
var actorSystem = ActorSystem.Create("DockerBootstrap", config);
diff --git a/src/Akka.Bootstrap.Docker.Tests/DockerBootstrapSpecs.cs b/src/Akka.Bootstrap.Docker.Tests/DockerBootstrapSpecs.cs
index f4d4757..5864eec 100644
--- a/src/Akka.Bootstrap.Docker.Tests/DockerBootstrapSpecs.cs
+++ b/src/Akka.Bootstrap.Docker.Tests/DockerBootstrapSpecs.cs
@@ -10,7 +10,6 @@
using Akka.Configuration;
using FluentAssertions;
using Xunit;
-using Hocon;
namespace Akka.Bootstrap.Docker.Tests
{
@@ -20,20 +19,18 @@ namespace Akka.Bootstrap.Docker.Tests
public class DockerBootstrapSpecs
{
[Theory]
- [InlineData("\"akka.tcp://MySys@localhost:9140\"")]
- [InlineData("\"akka.tcp://MySys@localhost:9140\", \"akka.tcp://MySys@localhost:9141\"")]
- [InlineData("\"akka.tcp://MySys@localhost:9140\", \"akka.tcp://MySys@localhost:9141\", \"akka.tcp://MySys@localhost:9142\"")]
+ [InlineData("akka.tcp://MySys@localhost:9140")]
+ [InlineData("akka.tcp://MySys@localhost:9140, akka.tcp://MySys@localhost:9141")]
+ [InlineData("akka.tcp://MySys@localhost:9140, akka.tcp://MySys@localhost:9141, akka.tcp://MySys@localhost:9142")]
public void ShouldStartIfValidSeedNodesIfSupplied(string seedNodes)
{
try
{
Environment.SetEnvironmentVariable("CLUSTER_SEEDS", seedNodes, EnvironmentVariableTarget.Process);
var myConfig = ConfigurationFactory.Empty.BootstrapFromDocker();
- Config expected = $"array=[{seedNodes}]";
-
myConfig.HasPath("akka.cluster.seed-nodes").Should().BeTrue();
- var seeds = myConfig.GetStringList("akka.cluster.seed-nodes");
- seeds.Should().BeEquivalentTo(expected.GetStringList("array"));
+ var seeds = myConfig.GetStringList("akka.cluster.seed-nodes").Select(x => x.Trim());
+ seeds.Should().BeEquivalentTo(seedNodes.Split(",").Select(x => x.Trim()));
}
finally
{
@@ -90,37 +87,23 @@ public void ShouldStartNormallyIfNotEnvironmentVariablesAreSupplied()
[Fact]
public void ShouldStartIfValidAkkaConfigurationSuppliedByEnvironmentVariables()
{
- try
- {
- Environment.SetEnvironmentVariable("AKKA__COORDINATED_SHUTDOWN__EXIT_CLR", "on", EnvironmentVariableTarget.Process);
- Environment.SetEnvironmentVariable("AKKA__ACTOR__PROVIDER", "cluster", EnvironmentVariableTarget.Process);
- Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__HOSTNAME", "127.0.0.1", EnvironmentVariableTarget.Process);
- Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__PUBLIC_HOSTNAME", "example.local", EnvironmentVariableTarget.Process);
- Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__PORT", "2559", EnvironmentVariableTarget.Process);
- Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__0", "demo", EnvironmentVariableTarget.Process);
- Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__1", "test", EnvironmentVariableTarget.Process);
- Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__2", "backup", EnvironmentVariableTarget.Process);
-
- var myConfig = ConfigurationFactory.Empty.BootstrapFromDocker();
+ Environment.SetEnvironmentVariable("AKKA__COORDINATED_SHUTDOWN__EXIT_CLR", "on", EnvironmentVariableTarget.Process);
+ Environment.SetEnvironmentVariable("AKKA__ACTOR__PROVIDER", "cluster", EnvironmentVariableTarget.Process);
+ Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__HOSTNAME", "127.0.0.1", EnvironmentVariableTarget.Process);
+ Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__PUBLIC_HOSTNAME", "example.local", EnvironmentVariableTarget.Process);
+ Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__PORT", "2559", EnvironmentVariableTarget.Process);
+ Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__0", "demo", EnvironmentVariableTarget.Process);
+ Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__1", "test", EnvironmentVariableTarget.Process);
+ Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__2", "backup", EnvironmentVariableTarget.Process);
- myConfig.GetBoolean("akka.coordinated-shutdown.exit-clr").Should().BeTrue();
- myConfig.GetString("akka.actor.provider").Should().Be("cluster");
- myConfig.GetString("akka.remote.dot-netty.tcp.hostname").Should().Be("127.0.0.1");
- myConfig.GetString("akka.remote.dot-netty.tcp.public-hostname").Should().Be("example.local");
- myConfig.GetInt("akka.remote.dot-netty.tcp.port").Should().Be(2559);
- myConfig.GetStringList("akka.cluster.roles").Should().BeEquivalentTo(new[] { "demo", "test", "backup" });
- }
- finally
- {
- Environment.SetEnvironmentVariable("AKKA__COORDINATED_SHUTDOWN__EXIT_CLR", null);
- Environment.SetEnvironmentVariable("AKKA__ACTOR__PROVIDER", null);
- Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__HOSTNAME", null);
- Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__PUBLIC_HOSTNAME", null);
- Environment.SetEnvironmentVariable("AKKA__REMOTE__DOT_NETTY__TCP__PORT", null);
- Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__0", null);
- Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__1", null);
- Environment.SetEnvironmentVariable("AKKA__CLUSTER__ROLES__2", null);
- }
+ var myConfig = ConfigurationFactory.Empty.BootstrapFromDocker();
+
+ myConfig.GetBoolean("akka.coordinated-shutdown.exit-clr").Should().BeTrue();
+ myConfig.GetString("akka.actor.provider").Should().Be("cluster");
+ myConfig.GetString("akka.remote.dot-netty.tcp.hostname").Should().Be("127.0.0.1");
+ myConfig.GetString("akka.remote.dot-netty.tcp.public-hostname").Should().Be("example.local");
+ myConfig.GetInt("akka.remote.dot-netty.tcp.port").Should().Be(2559);
+ myConfig.GetStringList("akka.cluster.roles").Should().BeEquivalentTo(new [] { "demo", "test", "backup" });
}
}
}
\ No newline at end of file
diff --git a/src/Akka.Bootstrap.Docker/Akka.Bootstrap.Docker.csproj b/src/Akka.Bootstrap.Docker/Akka.Bootstrap.Docker.csproj
index 97bed9b..4f668d3 100644
--- a/src/Akka.Bootstrap.Docker/Akka.Bootstrap.Docker.csproj
+++ b/src/Akka.Bootstrap.Docker/Akka.Bootstrap.Docker.csproj
@@ -14,14 +14,6 @@
bin\Release\netstandard1.6\Akka.Bootstrap.Docker.xml
-
-
-
-
-
-
-
-
diff --git a/src/Akka.Bootstrap.Docker/AssemblyMarker.cs b/src/Akka.Bootstrap.Docker/AssemblyMarker.cs
deleted file mode 100644
index 8521e96..0000000
--- a/src/Akka.Bootstrap.Docker/AssemblyMarker.cs
+++ /dev/null
@@ -1,10 +0,0 @@
-using System;
-using System.Collections.Generic;
-using System.Text;
-
-namespace Akka.Bootstrap.Docker
-{
- internal class AssemblyMarker
- {
- }
-}
diff --git a/src/Akka.Bootstrap.Docker/Docker.Environment.conf b/src/Akka.Bootstrap.Docker/Docker.Environment.conf
deleted file mode 100644
index 1f012fb..0000000
--- a/src/Akka.Bootstrap.Docker/Docker.Environment.conf
+++ /dev/null
@@ -1,7 +0,0 @@
-###############################################
-# Docker Environment Variable Overrides #
-###############################################
-
-akka.remote.dot-netty.tcp.public-hostname = ${?CLUSTER_IP}
-akka.remote.dot-netty.tcp.port = ${?CLUSTER_PORT}
-environment.seed-nodes = ${?CLUSTER_SEEDS}
\ No newline at end of file
diff --git a/src/Akka.Bootstrap.Docker/EnvironmentVariableConfigLoader.cs b/src/Akka.Bootstrap.Docker/EnvironmentVariableConfigLoader.cs
index 38c8919..ce4e4fb 100644
--- a/src/Akka.Bootstrap.Docker/EnvironmentVariableConfigLoader.cs
+++ b/src/Akka.Bootstrap.Docker/EnvironmentVariableConfigLoader.cs
@@ -10,7 +10,6 @@
using System.Linq;
using System.Text;
using Akka.Configuration;
-using System.Net;
using Hocon;
namespace Akka.Bootstrap.Docker
@@ -21,8 +20,6 @@ namespace Akka.Bootstrap.Docker
///
public static class EnvironmentVariableConfigLoader
{
- private const string DefaultConfigResource = "Akka.Bootstrap.Docker.Docker.Environment.conf";
-
private static IEnumerable GetEnvironmentVariables()
{
// Currently, exclude environment variables that do not start with "AKKA__"
@@ -31,11 +28,34 @@ private static IEnumerable GetEnvironmentV
// to other non "AKKA__" variables.
bool UseAllEnvironmentVariables = false;
+ // List of environment variable mappings that do not follow the "AKKA__" convention.
+ // We are currently supporting these out of convenience, and may choose to officially
+ // create a set of aliases in the future. Doing so would allow envvar configuration
+ // to be less verbose but might perpetuate confusion as to source of truth for keys.
+ Dictionary ExistingMappings = new Dictionary()
+ {
+ { "CLUSTER_IP", "akka.remote.dot-netty.tcp.public-hostname" },
+ { "CLUSTER_PORT", "akka.remote.dot-netty.tcp.port" },
+ { "CLUSTER_SEEDS", "akka.cluster.seed-nodes" }
+ };
+
+ // Identify environment variable mappings that are expected to be lists
+ string[] ExistingMappingLists = new string[] { "CLUSTER_SEEDS" };
+
foreach (DictionaryEntry set in Environment.GetEnvironmentVariables(EnvironmentVariableTarget.Process))
{
var key = set.Key.ToString();
var isList = false;
+ if (ExistingMappings.TryGetValue(key, out var mappedKey))
+ {
+ isList = ExistingMappingLists.Contains(key);
+
+ // Format the key to appear as if it were an environment variable
+ // in the "AKKA__" format
+ key = mappedKey.ToUpper().Replace(".", "__").Replace("-", "_");
+ }
+
if (!UseAllEnvironmentVariables)
if (!key.StartsWith("AKKA__", StringComparison.OrdinalIgnoreCase))
continue;
@@ -74,36 +94,31 @@ private static IEnumerable GetEnvironmentV
///
///
///
- public static Config FromEnvironment(this Config _)
+ public static Config FromEnvironment(this Config input)
{
- var environmentConfig = HoconConfigurationFactory.FromResource(DefaultConfigResource);
- var defaultValues = new StringBuilder();
- defaultValues.AppendLine($@"
- akka.remote.dot-netty.tcp {{
- hostname=0.0.0.0
- public-hostname={Dns.GetHostName()}
- }}");
- if (environmentConfig.HasPath("environment.seed-nodes"))
- defaultValues.AppendLine($"akka.cluster.seed-nodes=[{environmentConfig.GetString("environment.seed-nodes")}]");
-
var entries = GetEnvironmentVariables()
.OrderByDescending(x => x.Depth)
.GroupBy(x => x.Key);
+ StringBuilder sb = new StringBuilder();
foreach (var set in entries)
{
- defaultValues.Append($"{set.Key}=");
+ sb.Append($"{set.Key}=");
if (set.Count() > 1)
- {
- defaultValues.AppendLine($"[\n\t\"{String.Join("\",\n\t\"", set.OrderBy(y => y.Index).Select(y => y.Value.Trim()))}\"]");
+ {
+ sb.AppendLine($"[\n\t\"{String.Join("\",\n\t\"", set.OrderBy(y => y.Index).Select(y => y.Value.Trim()))}\"]");
}
else
{
- defaultValues.AppendLine($"{set.First().Value}");
+ sb.AppendLine($"{set.First().Value}");
}
}
- return environmentConfig.WithFallback(HoconConfigurationFactory.ParseString(defaultValues.ToString()));
+ if(sb.Length == 0)
+ return Config.Empty;
+ var config = ConfigurationFactory.ParseString(sb.ToString());
+
+ return config;
}
}
diff --git a/src/Akka.Bootstrap.ServiceFabric.Tests/ServiceFabricBootstrapSpecs.cs b/src/Akka.Bootstrap.ServiceFabric.Tests/ServiceFabricBootstrapSpecs.cs
index 118a6f7..4400648 100644
--- a/src/Akka.Bootstrap.ServiceFabric.Tests/ServiceFabricBootstrapSpecs.cs
+++ b/src/Akka.Bootstrap.ServiceFabric.Tests/ServiceFabricBootstrapSpecs.cs
@@ -7,6 +7,7 @@
using System;
using System.Linq;
using Akka.Configuration;
+using Hocon;
using FluentAssertions;
using Xunit;
diff --git a/src/common.props b/src/common.props
index 47f5c39..5ad10e6 100644
--- a/src/common.props
+++ b/src/common.props
@@ -1,6 +1,6 @@
- Copyright © 2015-2019 Petabridge®
+ Copyright © 2015-2020 Petabridge®
Petabridge
0.4.0
Upgraded to Akka.NET v1.4.1-rc1 and used native environment variable substitution from HOCON