Merge pull request #2039 from umbraco/temp-u4-10121

U4-10121 - Scheduled Publishing as background task
This commit is contained in:
Claus
2017-07-11 11:37:46 +02:00
committed by GitHub
3 changed files with 30 additions and 137 deletions

View File

@@ -1,12 +1,18 @@
using System;
using System.Net.Http;
using System.IO;
using System.Threading;
using System.Threading.Tasks;
using System.Web;
using System.Web.Hosting;
using umbraco;
using Umbraco.Core;
using Umbraco.Core.Configuration;
using Umbraco.Core.Configuration.UmbracoSettings;
using Umbraco.Core.Logging;
using Umbraco.Core.Publishing;
using Umbraco.Core.Sync;
using Umbraco.Web.Mvc;
using Umbraco.Web.Routing;
using Umbraco.Web.Security;
namespace Umbraco.Web.Scheduling
{
@@ -23,6 +29,8 @@ namespace Umbraco.Web.Scheduling
_settings = settings;
}
private ILogger Logger { get { return _appContext.ProfilingLogger.Logger; } }
public override async Task<bool> PerformRunAsync(CancellationToken token)
{
if (_appContext == null) return true; // repeat...
@@ -30,10 +38,10 @@ namespace Umbraco.Web.Scheduling
switch (_appContext.GetCurrentServerRole())
{
case ServerRole.Slave:
LogHelper.Debug<ScheduledPublishing>("Does not run on slave servers.");
Logger.Debug<ScheduledPublishing>("Does not run on slave servers.");
return true; // DO repeat, server role can change
case ServerRole.Unknown:
LogHelper.Debug<ScheduledPublishing>("Does not run on servers with unknown role.");
Logger.Debug<ScheduledPublishing>("Does not run on servers with unknown role.");
return true; // DO repeat, server role can change
}
@@ -44,72 +52,31 @@ namespace Umbraco.Web.Scheduling
return false; // do NOT repeat, going down
}
string umbracoAppUrl;
try
{
umbracoAppUrl = _appContext == null || _appContext.UmbracoApplicationUrl.IsNullOrWhiteSpace()
? null
: _appContext.UmbracoApplicationUrl;
if (umbracoAppUrl.IsNullOrWhiteSpace())
// DO not run publishing if content is re-loading
if (content.Instance.isInitializing == false)
{
LogHelper.Warn<ScheduledPublishing>("No url for service (yet), skip.");
return true; // repeat
//TODO: We should remove this in v8, this is a backwards compat hack
// because notifications will not be sent if there is no UmbracoContext
// see NotificationServiceExtensions
var httpContext = new HttpContextWrapper(new HttpContext(new SimpleWorkerRequest("temp.aspx", "", new StringWriter())));
UmbracoContext.EnsureContext(
httpContext,
_appContext,
new WebSecurity(httpContext, _appContext),
_settings,
UrlProviderResolver.Current.Providers,
true);
var publisher = new ScheduledPublisher(_appContext.Services.ContentService);
var count = publisher.CheckPendingAndProcess();
Logger.Debug<ScheduledPublishing>(() => string.Format("Processed {0} items", count));
}
}
catch (Exception e)
{
LogHelper.Error<ScheduledPublishing>("Could not acquire application url", e);
return true; // repeat
}
var url = umbracoAppUrl + "/RestServices/ScheduledPublish/Index";
using (DisposableTimer.DebugDuration<ScheduledPublishing>(
() => string.Format("Scheduled publishing executing @ {0}", url),
() => "Scheduled publishing complete"))
{
try
{
using (var wc = new HttpClient())
{
var request = new HttpRequestMessage(HttpMethod.Post, url)
{
Content = new StringContent(string.Empty)
};
// running on a background task, requires its own (safe) scope
// (GetAuthenticationHeaderValue uses UserService to load the current user, hence requires a database)
// (might not need a scope but we don't know really)
using (var scope = ApplicationContext.Current.ScopeProvider.CreateScope())
{
//pass custom the authorization header
request.Headers.Authorization = AdminTokenAuthorizeAttribute.GetAuthenticationHeaderValue(_appContext);
scope.Complete();
}
var result = await wc.SendAsync(request, token);
var content = await result.Content.ReadAsStringAsync();
if (result.IsSuccessStatusCode)
{
LogHelper.Debug<ScheduledPublishing>(
() => string.Format(
"Request successfully sent to url = \"{0}\". ", url));
}
else
{
var msg = string.Format(
"Request failed with status code \"{0}\". Request content = \"{1}\".",
result.StatusCode, content);
var ex = new HttpRequestException(msg);
LogHelper.Error<ScheduledPublishing>(msg, ex);
}
}
}
catch (Exception e)
{
LogHelper.Error<ScheduledPublishing>(string.Format("Failed (at \"{0}\").", umbracoAppUrl), e);
}
Logger.Error<ScheduledPublishing>("Failed (see exception).", e);
}
return true; // repeat

View File

@@ -1985,7 +1985,6 @@
<Compile Include="WebServices\ExamineManagementApiController.cs" />
<Compile Include="WebServices\FolderBrowserService.cs" />
<Compile Include="WebServices\TagsController.cs" />
<Compile Include="WebServices\ScheduledPublishController.cs" />
<Compile Include="WebServices\UmbracoAuthorizedHttpHandler.cs" />
<Compile Include="WebServices\SaveFileController.cs" />
<Compile Include="WebServices\UmbracoAuthorizedWebService.cs">

View File

@@ -1,73 +0,0 @@
using System;
using System.Web.Mvc;
using umbraco;
using Umbraco.Core.Logging;
using Umbraco.Core.Publishing;
using Umbraco.Web.Mvc;
namespace Umbraco.Web.WebServices
{
/// <summary>
/// A REST controller used for running the scheduled publishing, this is called from the background worker timer
/// </summary>
[AdminTokenAuthorize]
public class ScheduledPublishController : UmbracoController
{
private static bool _isPublishingRunning = false;
[HttpPost]
public JsonResult Index()
{
if (_isPublishingRunning)
{
Logger.Debug<ScheduledPublishController>(() => "Scheduled publishing is currently executing this request will exit");
return null;
}
_isPublishingRunning = true;
try
{
// DO not run publishing if content is re-loading
if (content.Instance.isInitializing == false)
{
var publisher = new ScheduledPublisher(Services.ContentService);
var count = publisher.CheckPendingAndProcess();
Logger.Debug<ScheduledPublishController>(() => string.Format("The scheduler processed {0} items", count));
}
return Json(new
{
success = true
});
}
catch (Exception ee)
{
var errorMessage = "Error executing scheduled task";
if (HttpContext != null && HttpContext.Request != null)
{
if (HttpContext.Request.Url != null)
errorMessage = string.Format("{0} | Request to {1}", errorMessage, HttpContext.Request.Url);
if (HttpContext.Request.UserHostAddress != null)
errorMessage = string.Format("{0} | Coming from {1}", errorMessage, HttpContext.Request.UserHostAddress);
if (HttpContext.Request.UrlReferrer != null)
errorMessage = string.Format("{0} | Referrer {1}", errorMessage, HttpContext.Request.UrlReferrer);
}
LogHelper.Error<ScheduledPublishController>(errorMessage, ee);
Response.StatusCode = 400;
return Json(new
{
success = false,
message = ee.Message
});
}
finally
{
_isPublishingRunning = false;
}
}
}
}