Skip to content

Commit

Permalink
Merge pull request #118 from MindaugasLaganeckas/master
Browse files Browse the repository at this point in the history
Feature: waitForHealthy where it will wait until the state is reported as Healthy
  • Loading branch information
Mario Toffia committed Oct 29, 2019
2 parents 605a2dc + 0c42096 commit 3a78a1e
Show file tree
Hide file tree
Showing 3 changed files with 58 additions and 0 deletions.
18 changes: 18 additions & 0 deletions Ductus.FluentDocker/Builders/ContainerBuilder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -463,6 +463,14 @@ public ContainerBuilder WaitForPort(string portAndProto, double millisTimeout =
_config.WaitForPort = new Tuple<string, string, long>(portAndProto, address, Convert.ToInt64(millisTimeout));
return this;
}

public ContainerBuilder WaitForHealthy(TimeSpan timeout = default)
{
if (timeout == default) timeout = TimeSpan.MaxValue;

_config.WaitForHealthy = new Tuple<long>(Convert.ToInt64(timeout.TotalMilliseconds));
return this;
}

public ContainerBuilder WaitForPort(string portAndProto, TimeSpan timeout = default, string address = null)
{
Expand Down Expand Up @@ -585,6 +593,16 @@ private void AddHooks(IService container)
service, "Wait for port");
});

// Wait for healthy when started
if (null != _config.WaitForHealthy)
container.AddHook(ServiceRunningState.Running,
service =>
{
Fd.DisposeOnException(svc =>
((IContainerService) service).WaitForHealthy(_config.WaitForHealthy.Item1),
service, "Wait for healthy");
});

// Wait for http when started
if (null != _config.WaitForHttp && 0 != _config.WaitForHttp.Count)
container.AddHook(ServiceRunningState.Running, service =>
Expand Down
2 changes: 2 additions & 0 deletions Ductus.FluentDocker/Model/Builders/ContainerBuilderConfig.cs
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@ public ContainerBuilderConfig()
public string[] Arguments { get; set; }
public Tuple<string /*portAndProto*/, string /*address*/ , long /*waitTimeout*/> WaitForPort { get; set; }

public Tuple<long /*waitTimeout*/> WaitForHealthy { get; set; }

public List<ContainerSpecificConfig.WaitForHttpParams> WaitForHttp { get; } =
new List<ContainerSpecificConfig.WaitForHttpParams>();

Expand Down
38 changes: 38 additions & 0 deletions Ductus.FluentDocker/Services/Extensions/ContainerExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -242,6 +242,44 @@ public static Processes GetRunningProcesses(this IContainerService service)

return service;
}

/// <summary>
/// Waits for the container to be in a healthy state
/// </summary>
/// <param name="service">The service to check processes within.</param>
/// <param name="millisTimeout">Timeout giving up the wait.</param>
/// <returns>The inparam service.</returns>
public static IContainerService WaitForHealthy(this IContainerService service, long millisTimeout = -1)
{
if (service == null)
return null;

Exception exception = null;
var stopwatch = Stopwatch.StartNew();
using (var mre = new ManualResetEventSlim())
{
Timer timer;
using (timer = new Timer(_ =>
{
var config = service.GetConfiguration(true);
if (config?.State?.Health?.Status == HealthState.Healthy)
mre.Set();
if (stopwatch.ElapsedMilliseconds > millisTimeout)
{
exception = new FluentDockerException($"Wait for healthy expired for container {service.Id}");
mre.Set();
}
}, null, 0, 500))

mre.Wait();
timer.Dispose();
}

if (exception != null)
throw exception;

return service;
}

/// <summary>
/// Waits using an arbitrary function.
Expand Down

0 comments on commit 3a78a1e

Please sign in to comment.