Skip to content

Commit

Permalink
Add ability to create clean as part of export request.
Browse files Browse the repository at this point in the history
  • Loading branch information
KevinJump committed Oct 3, 2023
1 parent e6b61eb commit d46ce81
Show file tree
Hide file tree
Showing 7 changed files with 76 additions and 24 deletions.
8 changes: 8 additions & 0 deletions uSync.BackOffice/Configuration/uSyncHandlerSettings.cs
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,14 @@ public class HandlerSettings
[DefaultValue("")]
public string Group { get; set; } = string.Empty;

/// <summary>
/// create a corresponding _clean file for this export
/// </summary>
/// <remarks>
/// the clean file will only get created if the item in question has children.
/// </remarks>
public bool CreateClean { get; set; } = false;

/// <summary>
/// Additional settings for the handler
/// </summary>
Expand Down
31 changes: 20 additions & 11 deletions uSync.BackOffice/Services/uSyncService_Single.cs
Original file line number Diff line number Diff line change
Expand Up @@ -18,19 +18,22 @@ namespace uSync.BackOffice
{

/// <summary>
/// Implimentation of paged import methods.
/// Implementation of paged import methods.
/// </summary>
public partial class uSyncService
{
/// <summary>
/// Peform a paged report against a given folder
/// Perform a paged report against a given folder
/// </summary>
public IEnumerable<uSyncAction> ReportPartial(string folder, uSyncPagedImportOptions options, out int total)
{
var orderedNodes = LoadOrderedNodes(folder);
return ReportPartial(orderedNodes, options, out total);
}

/// <summary>
/// perform a paged report with the supplied ordered nodes
/// </summary>
public IEnumerable<uSyncAction> ReportPartial(IList<OrderedNodeInfo> orderedNodes, uSyncPagedImportOptions options, out int total)
{
total = orderedNodes.Count;
Expand All @@ -53,16 +56,16 @@ public IEnumerable<uSyncAction> ReportPartial(IList<OrderedNodeInfo> orderedNode
{
lastType = itemType;
handlerPair = _handlerFactory.GetValidHandlerByTypeName(itemType, syncHandlerOptions);

handlerPair?.Handler.PreCacheFolderKeys(folder, orderedNodes.Select(x => x.Key).ToList());
}

if (handlerPair == null)
{
_logger.LogWarning("No handler was found for {alias} item might not process correctly", itemType);
_logger.LogWarning("No handler for {itemType} {alias}", itemType, item.Node.GetAlias());
continue;
}

handlerPair.Handler.PreCacheFolderKeys(folder, orderedNodes.Select(x => x.Key).ToList());

options.Callbacks?.Update.Invoke(item.Node.GetAlias(),
CalculateProgress(index, total, options.ProgressMin, options.ProgressMax), 100);

Expand All @@ -78,14 +81,17 @@ public IEnumerable<uSyncAction> ReportPartial(IList<OrderedNodeInfo> orderedNode
}

/// <summary>
/// Peform a paged Import against a given folder
/// Perform a paged Import against a given folder
/// </summary>
public IEnumerable<uSyncAction> ImportPartial(string folder, uSyncPagedImportOptions options, out int total)
{
var orderedNodes = LoadOrderedNodes(folder);
return ImportPartial(orderedNodes, options, out total);
}

/// <summary>
/// perform an import of items from the suppled ordered node list.
/// </summary>
public IEnumerable<uSyncAction> ImportPartial(IList<OrderedNodeInfo> orderedNodes, uSyncPagedImportOptions options, out int total)
{
lock (_importLock)
Expand Down Expand Up @@ -114,8 +120,8 @@ public IEnumerable<uSyncAction> ImportPartial(IList<OrderedNodeInfo> orderedNode
lastType = itemType;
handlerPair = _handlerFactory.GetValidHandlerByTypeName(itemType, syncHandlerOptions);

// special case, blueprints looks like IContent items, except they are slightly diffrent
// so we check for them speicifically and get the handler for the enity rather than the object type.
// special case, blueprints looks like IContent items, except they are slightly different
// so we check for them specifically and get the handler for the entity rather than the object type.
if (item.Node.IsContent() && item.Node.IsBlueprint())
{
lastType = UdiEntityType.DocumentBlueprint;
Expand Down Expand Up @@ -146,7 +152,7 @@ public IEnumerable<uSyncAction> ImportPartial(IList<OrderedNodeInfo> orderedNode
}

/// <summary>
/// Peform a paged Import second pass against a given folder
/// Perform a paged Import second pass against a given folder
/// </summary>
public IEnumerable<uSyncAction> ImportPartialSecondPass(IEnumerable<uSyncAction> actions, uSyncPagedImportOptions options)
{
Expand Down Expand Up @@ -193,7 +199,7 @@ public IEnumerable<uSyncAction> ImportPartialSecondPass(IEnumerable<uSyncAction>
}

/// <summary>
/// Peform a paged Import post import against a given folder
/// Perform a paged Import post import against a given folder
/// </summary>
public IEnumerable<uSyncAction> ImportPartialPostImport(IEnumerable<uSyncAction> actions, uSyncPagedImportOptions options)
{
Expand Down Expand Up @@ -247,7 +253,7 @@ public IEnumerable<uSyncAction> ImportPartialPostImport(IEnumerable<uSyncAction>
}

/// <summary>
/// Peform a paged Clean after import for a given folder
/// Perform a paged Clean after import for a given folder
/// </summary>
public IEnumerable<uSyncAction> ImportPostCleanFiles(IEnumerable<uSyncAction> actions, uSyncPagedImportOptions options)
{
Expand Down Expand Up @@ -343,6 +349,9 @@ public OrderedNodeInfo(string filename, XElement node)
/// </summary>
public XElement Node { get; set; }

/// <summary>
/// the Guid key for this item, so we can cache the list of keys
/// </summary>
public Guid Key { get; set; }

/// <summary>
Expand Down
3 changes: 3 additions & 0 deletions uSync.BackOffice/SyncHandlers/Handlers/ContentHandler.cs
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,9 @@ public ContentHandler(
this.serializer = syncItemFactory.GetSerializer<IContent>("ContentSerializer");
}

protected override bool HasChildren(IContent item)
=> contentService.HasChildren(item.Id);

/// <summary>
/// Get child items
/// </summary>
Expand Down
3 changes: 3 additions & 0 deletions uSync.BackOffice/SyncHandlers/Handlers/MediaHandler.cs
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,9 @@ public MediaHandler(
this.mediaService = mediaService;
}

protected override bool HasChildren(IMedia item)
=> mediaService.HasChildren(item.Id);

/// <inheritdoc/>
protected override IEnumerable<IEntity> GetChildItems(IEntity parent)
{
Expand Down
15 changes: 7 additions & 8 deletions uSync.BackOffice/SyncHandlers/Interfaces/ISyncHandler.cs
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,7 @@ public interface ISyncHandler
string EntityType { get; }

/// <summary>
/// The type name of the items hanled (Item.getType().ToString())
/// The type name of the items handled (Item.getType().ToString())
/// </summary>
string TypeName { get; }

Expand All @@ -95,7 +95,7 @@ public interface ISyncHandler
/// </summary>
/// <param name="folder">folder to use when exporting</param>
/// <param name="settings">Handler settings to use for export</param>
/// <param name="callback">Callbacks to keep UI uptodate</param>
/// <param name="callback">Callbacks to keep UI upto date</param>
/// <returns>List of actions detailing changes</returns>
IEnumerable<uSyncAction> ExportAll(string folder, HandlerSettings settings, SyncUpdateCallback callback);

Expand Down Expand Up @@ -124,7 +124,7 @@ public interface ISyncHandler
/// <param name="folder">folder to use when Importing</param>
/// <param name="settings">Handler settings to use for import</param>
/// <param name="force">Force the import even if the settings haven't changed</param>
/// <param name="callback">Callbacks to keep UI uptodate</param>
/// <param name="callback">Callbacks to keep UI upto date</param>
/// <returns>List of actions detailing changes</returns>
IEnumerable<uSyncAction> ImportAll(string folder, HandlerSettings settings, bool force, SyncUpdateCallback callback);

Expand All @@ -138,7 +138,7 @@ public interface ISyncHandler
/// </summary>
/// <param name="folder">folder to use when reporting</param>
/// <param name="settings">Handler settings to use for report</param>
/// <param name="callback">Callbacks to keep UI uptodate</param>
/// <param name="callback">Callbacks to keep UI upto date</param>
/// <returns>List of actions detailing changes</returns>
IEnumerable<uSyncAction> Report(string folder, HandlerSettings settings, SyncUpdateCallback callback);

Expand All @@ -154,12 +154,12 @@ public interface ISyncHandler
IEnumerable<uSyncAction> ImportSecondPass(uSyncAction action, HandlerSettings settings, uSyncImportOptions options);

/// <summary>
/// default impimentation, roothandler does do this.
/// default implementation, root handler does do this.
/// </summary>
Udi FindFromNode(XElement node) => null;

/// <summary>
/// is this a current node (roothandler can do this too)
/// is this a current node (root handler can do this too)
/// </summary>
ChangeType GetItemStatus(XElement node) => ChangeType.NoChange;

Expand All @@ -169,7 +169,6 @@ public interface ISyncHandler
/// </summary>
/// <param name="folder"></param>
/// <param name="keys"></param>
void PreCacheFolderKeys(string folder, IList<Guid> keys)
{ }
void PreCacheFolderKeys(string folder, IList<Guid> keys) { }
}
}
15 changes: 11 additions & 4 deletions uSync.BackOffice/SyncHandlers/SyncHandlerBase.cs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
using Umbraco.Cms.Core.Models.Entities;
using Umbraco.Cms.Core.Services;
using Umbraco.Cms.Core.Strings;
using Umbraco.Extensions;

using uSync.BackOffice.Configuration;
using uSync.BackOffice.Services;
Expand Down Expand Up @@ -53,6 +54,9 @@ public SyncHandlerBase(
this.entityService = entityService;
}

protected override bool HasChildren(TObject item)
=> entityService.GetChildren(item.Id).Any();

/// <summary>
/// given a folder we calculate what items we can remove, becuase they are
/// not in one the the files in the folder.
Expand Down Expand Up @@ -164,7 +168,12 @@ protected override IEnumerable<IEntity> GetChildItems(IEntity parent)
/// </summary>
virtual protected IEnumerable<IEntity> GetChildItems(int parent)
{
if (this.itemObjectType != UmbracoObjectTypes.Unknown)
if (this.itemObjectType == UmbracoObjectTypes.Unknown)
return Enumerable.Empty<IEntity>();

var cacheKey = $"{GetCacheKeyBase()}_parent_{parent}";

return runtimeCache.GetCacheItem(cacheKey, () =>
{
if (parent == -1)
{
Expand All @@ -176,9 +185,7 @@ virtual protected IEnumerable<IEntity> GetChildItems(int parent)
// load it, so GetChildren without the object type is quicker.
return entityService.GetChildren(parent);
}
}

return Enumerable.Empty<IEntity>();
}, null);
}

/// <summary>
Expand Down
25 changes: 24 additions & 1 deletion uSync.BackOffice/SyncHandlers/SyncHandlerRoot.cs
Original file line number Diff line number Diff line change
Expand Up @@ -864,6 +864,11 @@ virtual public IEnumerable<uSyncAction> Export(TObject item, string folder, Hand
{
// only write the file to disk if it should be exported.
syncFileService.SaveXElement(attempt.Item, filename);

if (config.CreateClean && HasChildren(item))
{
CreateCleanFile(GetItemKey(item), filename);
}
}
else
{
Expand All @@ -876,6 +881,24 @@ virtual public IEnumerable<uSyncAction> Export(TObject item, string folder, Hand
return uSyncActionHelper<XElement>.SetAction(attempt, filename, GetItemKey(item), this.Alias).AsEnumerableOfOne();
}

protected virtual bool HasChildren(TObject item)
=> true;

private void CreateCleanFile(Guid key, string filename)
{
if (string.IsNullOrWhiteSpace(filename) || key == Guid.Empty)
return;

var folder = Path.GetDirectoryName(filename);
var name = Path.GetFileNameWithoutExtension(filename);

var cleanPath = Path.Combine(folder, $"{name}_clean.config");

var node = XElementExtensions.MakeEmpty(key, SyncActionType.Clean, $"clean {name} children");
node.Add(new XAttribute("itemType", serializer.ItemType));
syncFileService.SaveXElement(node, cleanPath);
}

#endregion

#region Reporting
Expand Down Expand Up @@ -1760,7 +1783,7 @@ private string GetNameFromFileOrNode(string filename, XElement node)
=> !string.IsNullOrWhiteSpace(filename) ? filename : node.GetAlias();


private string GetCacheKeyBase()
protected string GetCacheKeyBase()
=> $"keycache_{this.Alias}_{Thread.CurrentThread.ManagedThreadId}";

private string PrepCaches()
Expand Down

0 comments on commit d46ce81

Please sign in to comment.