Changing the retry interval to 1 second with retry count = 60

Also exposing a host shutdown token to prevent retries after the process died.
This commit is contained in:
Praburaj 2015-04-15 16:59:48 -07:00
parent 64977e14a9
commit edec7e9cce
11 changed files with 99 additions and 34 deletions

View File

@ -1,4 +1,6 @@
namespace DeploymentHelpers
using System.Threading;
namespace DeploymentHelpers
{
/// <summary>
/// Result of a deployment.
@ -20,5 +22,10 @@
/// Original deployment parameters used for this deployment.
/// </summary>
public DeploymentParameters DeploymentParameters { get; set; }
/// <summary>
/// Triggered when the host process dies or pulled down.
/// </summary>
public CancellationToken HostShutdownToken { get; set; }
}
}

View File

@ -8,12 +8,28 @@ namespace DeploymentHelpers
{
public class RetryHelper
{
public static void RetryRequest(Func<HttpResponseMessage> retryBlock, ILogger logger, int retryCount = 12)
/// <summary>
/// Retries every 1 sec for 60 times by default.
/// </summary>
/// <param name="retryBlock"></param>
/// <param name="logger"></param>
/// <param name="cancellationToken"></param>
/// <param name="retryCount"></param>
public static void RetryRequest(
Func<HttpResponseMessage> retryBlock,
ILogger logger,
CancellationToken cancellationToken = default(CancellationToken),
int retryCount = 60)
{
for (int retry = 0; retry < retryCount; retry++)
{
try
{
if (cancellationToken.IsCancellationRequested)
{
break;
}
logger.LogWarning("Retry count {retryCount}..", retry + 1);
var response = retryBlock();
@ -41,7 +57,7 @@ namespace DeploymentHelpers
)
{
logger.LogWarning("Failed to complete the request : {0}.", exception.InnerException.Message);
Thread.Sleep(7 * 1000); //Wait for a while before retry.
Thread.Sleep(1 * 1000); //Wait for a while before retry.
}
}
}

View File

@ -3,6 +3,7 @@ using System.Diagnostics;
using System.IO;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading;
using Microsoft.Framework.Logging;
namespace DeploymentHelpers
@ -171,6 +172,18 @@ namespace DeploymentHelpers
}
}
protected void TriggerHostShutdown(CancellationTokenSource hostShutdownSource)
{
try
{
hostShutdownSource.Cancel();
}
catch (Exception)
{
// Suppress errors.
}
}
public abstract void Dispose();
}
}

View File

@ -2,6 +2,7 @@
using System;
using System.IO;
using System.Linq;
using System.Threading;
using System.Xml;
using Microsoft.Framework.Logging;
using Microsoft.Web.Administration;
@ -14,6 +15,7 @@ namespace DeploymentHelpers
public class IISDeployer : ApplicationDeployer
{
private IISApplication _application;
private CancellationTokenSource _hostShutdownToken = new CancellationTokenSource();
public IISDeployer(DeploymentParameters startParameters, ILogger logger)
: base(startParameters, logger)
@ -49,7 +51,8 @@ namespace DeploymentHelpers
WebRootLocation = DeploymentParameters.ApplicationPath,
DeploymentParameters = DeploymentParameters,
// Accomodate the vdir name.
ApplicationBaseUri = new UriBuilder(Uri.UriSchemeHttp, "localhost", _application.Port, _application.VirtualDirectoryName).Uri.AbsoluteUri + "/"
ApplicationBaseUri = new UriBuilder(Uri.UriSchemeHttp, "localhost", _application.Port, _application.VirtualDirectoryName).Uri.AbsoluteUri + "/",
HostShutdownToken = _hostShutdownToken.Token
};
}
@ -84,6 +87,8 @@ namespace DeploymentHelpers
if (_application != null)
{
_application.StopAndDeleteAppPool();
Logger.LogError("Application pool was shutdown successfully.");
TriggerHostShutdown(_hostShutdownToken);
}
CleanPublishedOutput();

View File

@ -1,6 +1,7 @@
using System;
using System.Diagnostics;
using System.IO;
using System.Threading;
using Microsoft.Framework.Logging;
using Microsoft.Framework.Runtime;
using Microsoft.Framework.Runtime.Infrastructure;
@ -29,18 +30,19 @@ namespace DeploymentHelpers
}
// Launch the host process.
_hostProcess = StartHeliosHost();
var hostExitToken = StartHeliosHost();
return new DeploymentResult
{
WebRootLocation = DeploymentParameters.ApplicationPath,
DeploymentParameters = DeploymentParameters,
// Right now this works only for urls like http://localhost:5001/. Does not work for http://localhost:5001/subpath.
ApplicationBaseUri = DeploymentParameters.ApplicationBaseUriHint
ApplicationBaseUri = DeploymentParameters.ApplicationBaseUriHint,
HostShutdownToken = hostExitToken
};
}
private Process StartHeliosHost()
private CancellationToken StartHeliosHost()
{
if (!string.IsNullOrWhiteSpace(DeploymentParameters.ApplicationHostConfigTemplateContent))
{
@ -96,16 +98,21 @@ namespace DeploymentHelpers
startInfo.Environment["DNX_APPBASE"] = DeploymentParameters.ApplicationPath;
#endif
var hostProcess = Process.Start(startInfo);
if (hostProcess.HasExited)
_hostProcess = Process.Start(startInfo);
var hostExitTokenSource = new CancellationTokenSource();
_hostProcess.Exited += (sender, e) =>
{
Logger.LogError("Host process {processName} exited with code {exitCode} or failed to start.", startInfo.FileName, hostProcess.ExitCode);
TriggerHostShutdown(hostExitTokenSource);
};
if (_hostProcess.HasExited)
{
Logger.LogError("Host process {processName} exited with code {exitCode} or failed to start.", startInfo.FileName, _hostProcess.ExitCode);
throw new Exception("Failed to start host");
}
Logger.LogInformation("Started iisexpress. Process Id : {processId}", hostProcess.Id);
return hostProcess;
Logger.LogInformation("Started iisexpress. Process Id : {processId}", _hostProcess.Id);
return hostExitTokenSource.Token;
}
private void CopyAspNetLoader()

View File

@ -2,6 +2,7 @@
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Threading;
using Microsoft.Framework.Logging;
namespace DeploymentHelpers
@ -37,17 +38,18 @@ namespace DeploymentHelpers
}
// Launch the host process.
_hostProcess = StartMonoHost();
var hostExitToken = StartMonoHost();
return new DeploymentResult
{
WebRootLocation = DeploymentParameters.ApplicationPath,
DeploymentParameters = DeploymentParameters,
ApplicationBaseUri = DeploymentParameters.ApplicationBaseUriHint
ApplicationBaseUri = DeploymentParameters.ApplicationBaseUriHint,
HostShutdownToken = hostExitToken
};
}
private Process StartMonoHost()
private CancellationToken StartMonoHost()
{
if (DeploymentParameters.ServerType != ServerType.Kestrel)
{
@ -66,16 +68,23 @@ namespace DeploymentHelpers
RedirectStandardInput = true
};
var hostProcess = Process.Start(startInfo);
Logger.LogInformation("Started {0}. Process Id : {1}", hostProcess.MainModule.FileName, hostProcess.Id);
if (hostProcess.HasExited)
_hostProcess = Process.Start(startInfo);
var hostExitTokenSource = new CancellationTokenSource();
_hostProcess.Exited += (sender, e) =>
{
Logger.LogError("Host process {processName} exited with code {exitCode} or failed to start.", startInfo.FileName, hostProcess.ExitCode);
Logger.LogError("Host process {processName} exited with code {exitCode}.", startInfo.FileName, _hostProcess.ExitCode);
TriggerHostShutdown(hostExitTokenSource);
};
Logger.LogInformation("Started {0}. Process Id : {1}", _hostProcess.MainModule.FileName, _hostProcess.Id);
if (_hostProcess.HasExited)
{
Logger.LogError("Host process {processName} exited with code {exitCode} or failed to start.", startInfo.FileName, _hostProcess.ExitCode);
throw new Exception("Failed to start host");
}
return hostProcess;
return hostExitTokenSource.Token;
}
public override void Dispose()

View File

@ -1,6 +1,7 @@
using System;
using System.Diagnostics;
using System.IO;
using System.Threading;
using Microsoft.Framework.Logging;
namespace DeploymentHelpers
@ -27,17 +28,18 @@ namespace DeploymentHelpers
}
// Launch the host process.
_hostProcess = StartSelfHost();
var hostExitToken = StartSelfHost();
return new DeploymentResult
{
WebRootLocation = DeploymentParameters.ApplicationPath,
DeploymentParameters = DeploymentParameters,
ApplicationBaseUri = DeploymentParameters.ApplicationBaseUriHint
ApplicationBaseUri = DeploymentParameters.ApplicationBaseUriHint,
HostShutdownToken = hostExitToken
};
}
private Process StartSelfHost()
private CancellationToken StartSelfHost()
{
var commandName = DeploymentParameters.ServerType == ServerType.WebListener ? "web" : "kestrel";
Logger.LogInformation("Executing dnx.exe {appPath} {command} --server.urls {url}", DeploymentParameters.ApplicationPath, commandName, DeploymentParameters.ApplicationBaseUriHint);
@ -52,15 +54,21 @@ namespace DeploymentHelpers
AddEnvironmentVariablesToProcess(startInfo);
var hostProcess = Process.Start(startInfo);
if (hostProcess.HasExited)
_hostProcess = Process.Start(startInfo);
var hostExitTokenSource = new CancellationTokenSource();
_hostProcess.Exited += (sender, e) =>
{
Logger.LogError("Host process {processName} exited with code {exitCode} or failed to start.", startInfo.FileName, hostProcess.ExitCode);
TriggerHostShutdown(hostExitTokenSource);
};
if (_hostProcess.HasExited)
{
Logger.LogError("Host process {processName} exited with code {exitCode} or failed to start.", startInfo.FileName, _hostProcess.ExitCode);
throw new Exception("Failed to start host");
}
Logger.LogInformation("Started {fileName}. Process Id : {processId}", startInfo.FileName, hostProcess.Id);
return hostProcess;
Logger.LogInformation("Started {fileName}. Process Id : {processId}", startInfo.FileName, _hostProcess.Id);
return hostExitTokenSource.Token;
}
public override void Dispose()

View File

@ -70,7 +70,7 @@ namespace E2ETests
{
response = httpClient.GetAsync(string.Empty).Result;
return response;
}, logger: logger);
}, logger: logger, cancellationToken: deploymentResult.HostShutdownToken);
logger.LogInformation("[Time]: Approximate time taken for application initialization : '{t}' seconds", stopwatch.Elapsed.TotalSeconds);

View File

@ -79,7 +79,7 @@ namespace E2ETests
{
response = httpClient.GetAsync(string.Empty).Result;
return response;
}, logger: logger);
}, logger: logger, cancellationToken: deploymentResult.HostShutdownToken);
logger.LogInformation("[Time]: Approximate time taken for application initialization : '{t}' seconds", stopwatch.Elapsed.TotalSeconds);

View File

@ -102,7 +102,7 @@ namespace E2ETests
{
response = httpClient.GetAsync(string.Empty).Result;
return response;
}, logger: logger);
}, logger: logger, cancellationToken: deploymentResult.HostShutdownToken);
logger.LogInformation("[Time]: Approximate time taken for application initialization : '{t}' seconds", stopwatch.Elapsed.TotalSeconds);

View File

@ -171,7 +171,7 @@ namespace E2ETests
{
response = httpClient.GetAsync(string.Empty).Result;
return response;
}, logger: logger);
}, logger: logger, cancellationToken: deploymentResult.HostShutdownToken);
logger.LogInformation("[Time]: Approximate time taken for application initialization : '{t}' seconds", stopwatch.Elapsed.TotalSeconds);