using System.IO; using System.Threading.Tasks; using Microsoft.AspNetCore.Http.Extensions; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Routing; using Microsoft.Extensions.Logging; using Microsoft.Extensions.Options; using Umbraco.Cms.Core; using Umbraco.Cms.Core.Configuration; using Umbraco.Cms.Core.Configuration.Models; using Umbraco.Cms.Core.Hosting; using Umbraco.Cms.Core.Security; using Umbraco.Cms.Core.Services; using Umbraco.Cms.Core.WebAssets; using Umbraco.Cms.Infrastructure.Install; using Umbraco.Cms.Web.Common.Attributes; using Umbraco.Cms.Web.Common.Filters; using Umbraco.Extensions; namespace Umbraco.Cms.Web.BackOffice.Install { /// /// The Installation controller /// [InstallAuthorize] [Area(Cms.Core.Constants.Web.Mvc.InstallArea)] public class InstallController : Controller { private readonly IBackOfficeSecurityAccessor _backofficeSecurityAccessor; private readonly InstallHelper _installHelper; private readonly IRuntimeState _runtime; private readonly GlobalSettings _globalSettings; private readonly IHostingEnvironment _hostingEnvironment; private readonly IUmbracoVersion _umbracoVersion; private readonly ILogger _logger; private readonly LinkGenerator _linkGenerator; private readonly IRuntimeMinifier _runtimeMinifier; public InstallController( IBackOfficeSecurityAccessor backofficeSecurityAccessor, InstallHelper installHelper, IRuntimeState runtime, IOptions globalSettings, IRuntimeMinifier runtimeMinifier, IHostingEnvironment hostingEnvironment, IUmbracoVersion umbracoVersion, ILogger logger, LinkGenerator linkGenerator) { _backofficeSecurityAccessor = backofficeSecurityAccessor; _installHelper = installHelper; _runtime = runtime; _globalSettings = globalSettings.Value; _runtimeMinifier = runtimeMinifier; _hostingEnvironment = hostingEnvironment; _umbracoVersion = umbracoVersion; _logger = logger; _linkGenerator = linkGenerator; } [HttpGet] [StatusCodeResult(System.Net.HttpStatusCode.ServiceUnavailable)] [TypeFilter(typeof(StatusCodeResultAttribute), Arguments = new object []{System.Net.HttpStatusCode.ServiceUnavailable})] public async Task Index() { var umbracoPath = Url.GetBackOfficeUrl(); if (_runtime.Level == RuntimeLevel.Run) return Redirect(umbracoPath); // TODO: Update for package migrations if (_runtime.Level == RuntimeLevel.Upgrade) { // Update ClientDependency version and delete its temp directories to make sure we get fresh caches _runtimeMinifier.Reset(); var authResult = await this.AuthenticateBackOfficeAsync(); if (!authResult.Succeeded) { return Redirect(_globalSettings.UmbracoPath + "/AuthorizeUpgrade?redir=" + Request.GetEncodedUrl()); } } // gen the install base URL ViewData.SetInstallApiBaseUrl(_linkGenerator.GetInstallerApiUrl()); // get the base umbraco folder var baseFolder = _hostingEnvironment.ToAbsolute(_globalSettings.UmbracoPath); ViewData.SetUmbracoBaseFolder(baseFolder); ViewData.SetUmbracoVersion(_umbracoVersion.SemanticVersion); await _installHelper.SetInstallStatusAsync(false, ""); return View(Path.Combine(Constants.SystemDirectories.Umbraco.TrimStart("~") , Cms.Core.Constants.Web.Mvc.InstallArea, nameof(Index) + ".cshtml")); } /// /// Used to perform the redirect to the installer when the runtime level is or /// /// [HttpGet] [IgnoreFromNotFoundSelectorPolicy] public ActionResult Redirect() { var uri = HttpContext.Request.GetEncodedUrl(); // redirect to install ReportRuntime(_logger, _runtime.Level, "Umbraco must install or upgrade."); var installUrl = $"{_linkGenerator.GetInstallerUrl()}?redir=true&url={uri}"; return Redirect(installUrl); } private static bool _reported; private static RuntimeLevel _reportedLevel; private static void ReportRuntime(ILogger logger, RuntimeLevel level, string message) { if (_reported && _reportedLevel == level) return; _reported = true; _reportedLevel = level; logger.LogWarning(message); } } }