mirror of
https://github.com/OrchardCMS/Orchard.git
synced 2026-02-09 09:16:41 +08:00
Implementing proper package uninstall process with features being disabled and uninstalled, then the package being removed.
This commit is contained in:
@@ -110,6 +110,7 @@
|
||||
<Compile Include="Services\PackageInstaller.cs" />
|
||||
<Compile Include="Services\PackageManager.cs" />
|
||||
<Compile Include="Models\PackagingEntry.cs" />
|
||||
<Compile Include="Services\PackageUninstallHandler.cs" />
|
||||
<Compile Include="Services\PackageUpdateManager.cs" />
|
||||
<Compile Include="Services\PackagingSourceManager.cs" />
|
||||
<Compile Include="ViewModels\PackagingAddSourceViewModel.cs" />
|
||||
|
||||
@@ -5,6 +5,8 @@ using NuGet;
|
||||
using Orchard.Environment.Extensions;
|
||||
using Orchard.Environment.Extensions.Folders;
|
||||
using Orchard.Environment.Extensions.Models;
|
||||
using Orchard.Environment.Features;
|
||||
using Orchard.Environment.State;
|
||||
using Orchard.Localization;
|
||||
using Orchard.Packaging.Models;
|
||||
|
||||
@@ -14,14 +16,23 @@ namespace Orchard.Packaging.Services {
|
||||
private readonly IExtensionManager _extensionManager;
|
||||
private readonly IPackageBuilder _packageBuilder;
|
||||
private readonly IPackageInstaller _packageInstaller;
|
||||
private readonly IShellStateManager _shellStateManager;
|
||||
private readonly IFeatureManager _featureManager;
|
||||
private readonly IPackageUninstallHandler _packageUninstallHandler;
|
||||
|
||||
public PackageManager(
|
||||
IExtensionManager extensionManager,
|
||||
IPackageBuilder packageBuilder,
|
||||
IPackageInstaller packageInstaller) {
|
||||
IPackageInstaller packageInstaller,
|
||||
IShellStateManager shellStateManager,
|
||||
IFeatureManager featureManager,
|
||||
IPackageUninstallHandler packageUninstallHandler) {
|
||||
_extensionManager = extensionManager;
|
||||
_packageBuilder = packageBuilder;
|
||||
_packageInstaller = packageInstaller;
|
||||
_shellStateManager = shellStateManager;
|
||||
_featureManager = featureManager;
|
||||
_packageUninstallHandler = packageUninstallHandler;
|
||||
|
||||
T = NullLocalizer.Instance;
|
||||
}
|
||||
@@ -69,7 +80,30 @@ namespace Orchard.Packaging.Services {
|
||||
}
|
||||
|
||||
public void Uninstall(string packageId, string applicationPath) {
|
||||
_packageInstaller.Uninstall(packageId, applicationPath);
|
||||
var extensionToUninstall = _extensionManager.AvailableExtensions()
|
||||
.FirstOrDefault(extension => PackageBuilder.BuildPackageId(extension.Id, extension.ExtensionType) == packageId);
|
||||
|
||||
if (extensionToUninstall == null) {
|
||||
throw new OrchardException(T("There is no extension that has the package ID \"{0}\".", packageId));
|
||||
}
|
||||
|
||||
var featureIdsToUninstall = extensionToUninstall.Features.Select(feature => feature.Id);
|
||||
var shellState = _shellStateManager.GetShellState();
|
||||
var featureStates = shellState.Features.Where(featureState => featureIdsToUninstall.Contains(featureState.Name));
|
||||
|
||||
// This means that no feature from this extension wasn enabled yet, can be uninstalled directly.
|
||||
if (!featureStates.Any()) {
|
||||
_packageUninstallHandler.QueuePackageUninstall(packageId);
|
||||
}
|
||||
else {
|
||||
_featureManager.DisableFeatures(extensionToUninstall.Features.Select(feature => feature.Id), true);
|
||||
|
||||
// Installed state can't be deduced from the shell state changes like for enabled state, so have to
|
||||
// set that explicitly.
|
||||
foreach (var featureState in featureStates) {
|
||||
_shellStateManager.UpdateInstalledState(featureState, Environment.State.Models.ShellFeatureState.State.Falling);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Web;
|
||||
using Orchard.Environment;
|
||||
using Orchard.Environment.Configuration;
|
||||
using Orchard.Environment.Descriptor;
|
||||
using Orchard.Environment.Extensions.Models;
|
||||
using Orchard.Environment.State;
|
||||
using Orchard.Events;
|
||||
|
||||
namespace Orchard.Packaging.Services {
|
||||
public interface IPackageUninstallHandler : IEventHandler {
|
||||
/// <summary>
|
||||
/// Queues a package to be uninstalled after the request is processed.
|
||||
/// </summary>
|
||||
/// <param name="packageId">The textual ID of the package.</param>
|
||||
void QueuePackageUninstall(string packageId);
|
||||
|
||||
/// <summary>
|
||||
/// Uninstalls the given package from the system.
|
||||
/// </summary>
|
||||
/// <param name="packageId">The textual ID of the package.</param>
|
||||
void UninstallPackage(string packageId);
|
||||
}
|
||||
|
||||
public class PackageUninstallHandler : IFeatureEventHandler, IPackageUninstallHandler {
|
||||
private readonly ShellSettings _shellSettings;
|
||||
private readonly IShellDescriptorManager _shellDescriptorManager;
|
||||
private readonly IProcessingEngine _processingEngine;
|
||||
private readonly IHostEnvironment _hostEnvironment;
|
||||
private readonly IPackageInstaller _packageInstaller;
|
||||
|
||||
public PackageUninstallHandler(
|
||||
ShellSettings shellSettings,
|
||||
IShellDescriptorManager shellDescriptorManager,
|
||||
IProcessingEngine processingEngine,
|
||||
IHostEnvironment hostEnvironment,
|
||||
IPackageInstaller packageInstaller) {
|
||||
_shellSettings = shellSettings;
|
||||
_shellDescriptorManager = shellDescriptorManager;
|
||||
_processingEngine = processingEngine;
|
||||
_hostEnvironment = hostEnvironment;
|
||||
_packageInstaller = packageInstaller;
|
||||
}
|
||||
|
||||
public void Installing(Feature feature) {
|
||||
}
|
||||
|
||||
public void Installed(Feature feature) {
|
||||
}
|
||||
|
||||
public void Enabling(Feature feature) {
|
||||
}
|
||||
|
||||
public void Enabled(Feature feature) {
|
||||
}
|
||||
|
||||
public void Disabling(Feature feature) {
|
||||
}
|
||||
|
||||
public void Disabled(Feature feature) {
|
||||
}
|
||||
|
||||
public void Uninstalling(Feature feature) {
|
||||
}
|
||||
|
||||
public void Uninstalled(Feature feature) {
|
||||
QueuePackageUninstall(PackageBuilder.BuildPackageId(feature.Descriptor.Extension.Id, feature.Descriptor.Extension.ExtensionType));
|
||||
}
|
||||
|
||||
public void QueuePackageUninstall(string packageId) {
|
||||
_processingEngine.AddTask(
|
||||
_shellSettings,
|
||||
_shellDescriptorManager.GetShellDescriptor(),
|
||||
"IPackageUninstallHandler.UninstallPackage",
|
||||
new Dictionary<string, object> { { "packageId", packageId } });
|
||||
}
|
||||
|
||||
public void UninstallPackage(string packageId) {
|
||||
_packageInstaller.Uninstall(packageId, _hostEnvironment.MapPath("~/"));
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user