Have the macro repository working, just need to write more unit tests regarding macro properties.
This commit is contained in:
93
src/Umbraco.Core/Models/IMacro.cs
Normal file
93
src/Umbraco.Core/Models/IMacro.cs
Normal file
@@ -0,0 +1,93 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Runtime.Serialization;
|
||||
using Umbraco.Core.Models.EntityBase;
|
||||
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines a Macro
|
||||
/// </summary>
|
||||
internal interface IMacro : IAggregateRoot
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the alias of the Macro
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
string Alias { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the name of the Macro
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
string Name { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a boolean indicating whether the Macro can be used in an Editor
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
bool UseInEditor { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Cache Duration for the Macro
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
int CacheDuration { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a boolean indicating whether the Macro should be Cached by Page
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
bool CacheByPage { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a boolean indicating whether the Macro should be Cached Personally
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
bool CacheByMember { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a boolean indicating whether the Macro should be rendered in an Editor
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
bool DontRender { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the path to user control or the Control Type to render
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
string ControlType { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the name of the assembly, which should be used by the Macro
|
||||
/// </summary>
|
||||
/// <remarks>Will usually only be filled if the ScriptFile is a Usercontrol</remarks>
|
||||
[DataMember]
|
||||
string ControlAssembly { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or set the path to the Python file in use
|
||||
/// </summary>
|
||||
/// <remarks>Optional: Can only be one of three Script, Python or Xslt</remarks>
|
||||
[DataMember]
|
||||
string ScriptPath { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the path to the Xslt file in use
|
||||
/// </summary>
|
||||
/// <remarks>Optional: Can only be one of three Script, Python or Xslt</remarks>
|
||||
[DataMember]
|
||||
string XsltPath { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a list of Macro Properties
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
MacroPropertyCollection Properties { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Returns an enum <see cref="MacroTypes"/> based on the properties on the Macro
|
||||
/// </summary>
|
||||
/// <returns><see cref="MacroTypes"/></returns>
|
||||
MacroTypes MacroType();
|
||||
}
|
||||
}
|
||||
39
src/Umbraco.Core/Models/IMacroProperty.cs
Normal file
39
src/Umbraco.Core/Models/IMacroProperty.cs
Normal file
@@ -0,0 +1,39 @@
|
||||
using System.Runtime.Serialization;
|
||||
using Umbraco.Core.Models.EntityBase;
|
||||
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines a Property for a Macro
|
||||
/// </summary>
|
||||
internal interface IMacroProperty : IValueObject
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the Alias of the Property
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
string Alias { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Name of the Property
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
string Name { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Sort Order of the Property
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
int SortOrder { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Type for this Property
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// The MacroPropertyTypes acts as a plugin for Macros.
|
||||
/// All types was previously contained in the database, but has been ported to code.
|
||||
/// </remarks>
|
||||
[DataMember]
|
||||
IMacroPropertyType PropertyType { get; set; }
|
||||
}
|
||||
}
|
||||
28
src/Umbraco.Core/Models/IMacroPropertyType.cs
Normal file
28
src/Umbraco.Core/Models/IMacroPropertyType.cs
Normal file
@@ -0,0 +1,28 @@
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines a PropertyType (plugin) for a Macro
|
||||
/// </summary>
|
||||
internal interface IMacroPropertyType
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the unique Alias of the Property Type
|
||||
/// </summary>
|
||||
string Alias { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the name of the Assembly used to render the Property Type
|
||||
/// </summary>
|
||||
string RenderingAssembly { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the name of the Type used to render the Property Type
|
||||
/// </summary>
|
||||
string RenderingType { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the Base Type for storing the PropertyType (Int32, String, Boolean)
|
||||
/// </summary>
|
||||
MacroPropertyTypeBaseTypes BaseType { get; }
|
||||
}
|
||||
}
|
||||
400
src/Umbraco.Core/Models/Macro.cs
Normal file
400
src/Umbraco.Core/Models/Macro.cs
Normal file
@@ -0,0 +1,400 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Collections.Specialized;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using System.Runtime.Serialization;
|
||||
using System.Text.RegularExpressions;
|
||||
using Umbraco.Core.IO;
|
||||
using Umbraco.Core.Models.EntityBase;
|
||||
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents a Macro
|
||||
/// </summary>
|
||||
[Serializable]
|
||||
[DataContract(IsReference = true)]
|
||||
internal class Macro : Entity, IMacro
|
||||
{
|
||||
public Macro()
|
||||
{
|
||||
_properties = new MacroPropertyCollection();
|
||||
_properties.CollectionChanged += PropertiesChanged;
|
||||
_addedProperties = new List<string>();
|
||||
_removedProperties = new List<string>();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates an item with pre-filled properties
|
||||
/// </summary>
|
||||
/// <param name="id"></param>
|
||||
/// <param name="useInEditor"></param>
|
||||
/// <param name="cacheDuration"></param>
|
||||
/// <param name="alias"></param>
|
||||
/// <param name="name"></param>
|
||||
/// <param name="controlType"></param>
|
||||
/// <param name="controlAssembly"></param>
|
||||
/// <param name="xsltPath"></param>
|
||||
/// <param name="cacheByPage"></param>
|
||||
/// <param name="cacheByMember"></param>
|
||||
/// <param name="dontRender"></param>
|
||||
/// <param name="scriptPath"></param>
|
||||
public Macro(int id, bool useInEditor, int cacheDuration, string @alias, string name, string controlType, string controlAssembly, string xsltPath, bool cacheByPage, bool cacheByMember, bool dontRender, string scriptPath)
|
||||
: this()
|
||||
{
|
||||
Id = id;
|
||||
UseInEditor = useInEditor;
|
||||
CacheDuration = cacheDuration;
|
||||
Alias = alias;
|
||||
Name = name;
|
||||
ControlType = controlType;
|
||||
ControlAssembly = controlAssembly;
|
||||
XsltPath = xsltPath;
|
||||
CacheByPage = cacheByPage;
|
||||
CacheByMember = cacheByMember;
|
||||
DontRender = dontRender;
|
||||
ScriptPath = scriptPath;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates an instance for persisting a new item
|
||||
/// </summary>
|
||||
/// <param name="useInEditor"></param>
|
||||
/// <param name="cacheDuration"></param>
|
||||
/// <param name="alias"></param>
|
||||
/// <param name="name"></param>
|
||||
/// <param name="controlType"></param>
|
||||
/// <param name="controlAssembly"></param>
|
||||
/// <param name="xsltPath"></param>
|
||||
/// <param name="cacheByPage"></param>
|
||||
/// <param name="cacheByMember"></param>
|
||||
/// <param name="dontRender"></param>
|
||||
/// <param name="scriptPath"></param>
|
||||
public Macro(string @alias, string name,
|
||||
string controlType = "",
|
||||
string controlAssembly = "",
|
||||
string xsltPath = "",
|
||||
string scriptPath = "",
|
||||
bool cacheByPage = false,
|
||||
bool cacheByMember = false,
|
||||
bool dontRender = true,
|
||||
bool useInEditor = false,
|
||||
int cacheDuration = 0)
|
||||
: this()
|
||||
{
|
||||
UseInEditor = useInEditor;
|
||||
CacheDuration = cacheDuration;
|
||||
Alias = alias;
|
||||
Name = name;
|
||||
ControlType = controlType;
|
||||
ControlAssembly = controlAssembly;
|
||||
XsltPath = xsltPath;
|
||||
CacheByPage = cacheByPage;
|
||||
CacheByMember = cacheByMember;
|
||||
DontRender = dontRender;
|
||||
ScriptPath = scriptPath;
|
||||
}
|
||||
|
||||
private string _alias;
|
||||
private string _name;
|
||||
private bool _useInEditor;
|
||||
private int _cacheDuration;
|
||||
private bool _cacheByPage;
|
||||
private bool _cacheByMember;
|
||||
private bool _dontRender;
|
||||
private string _scriptFile;
|
||||
private string _scriptAssembly;
|
||||
private string _python;
|
||||
private string _xslt;
|
||||
private readonly MacroPropertyCollection _properties;
|
||||
private readonly List<string> _addedProperties;
|
||||
private readonly List<string> _removedProperties;
|
||||
|
||||
private static readonly PropertyInfo AliasSelector = ExpressionHelper.GetPropertyInfo<Macro, string>(x => x.Alias);
|
||||
private static readonly PropertyInfo NameSelector = ExpressionHelper.GetPropertyInfo<Macro, string>(x => x.Name);
|
||||
private static readonly PropertyInfo UseInEditorSelector = ExpressionHelper.GetPropertyInfo<Macro, bool>(x => x.UseInEditor);
|
||||
private static readonly PropertyInfo CacheDurationSelector = ExpressionHelper.GetPropertyInfo<Macro, int>(x => x.CacheDuration);
|
||||
private static readonly PropertyInfo CacheByPageSelector = ExpressionHelper.GetPropertyInfo<Macro, bool>(x => x.CacheByPage);
|
||||
private static readonly PropertyInfo CacheByMemberSelector = ExpressionHelper.GetPropertyInfo<Macro, bool>(x => x.CacheByMember);
|
||||
private static readonly PropertyInfo DontRenderSelector = ExpressionHelper.GetPropertyInfo<Macro, bool>(x => x.DontRender);
|
||||
private static readonly PropertyInfo ControlPathSelector = ExpressionHelper.GetPropertyInfo<Macro, string>(x => x.ControlType);
|
||||
private static readonly PropertyInfo ControlAssemblySelector = ExpressionHelper.GetPropertyInfo<Macro, string>(x => x.ControlAssembly);
|
||||
private static readonly PropertyInfo ScriptPathSelector = ExpressionHelper.GetPropertyInfo<Macro, string>(x => x.ScriptPath);
|
||||
private static readonly PropertyInfo XsltPathSelector = ExpressionHelper.GetPropertyInfo<Macro, string>(x => x.XsltPath);
|
||||
private static readonly PropertyInfo PropertiesSelector = ExpressionHelper.GetPropertyInfo<Macro, MacroPropertyCollection>(x => x.Properties);
|
||||
|
||||
protected void PropertiesChanged(object sender, NotifyCollectionChangedEventArgs e)
|
||||
{
|
||||
OnPropertyChanged(PropertiesSelector);
|
||||
|
||||
if (e.Action == NotifyCollectionChangedAction.Add)
|
||||
{
|
||||
var alias = e.NewItems.Cast<IMacroProperty>().Select(x => x.Alias).First();
|
||||
|
||||
//remove from the removed/added props (since people could add/remove all they want in one request)
|
||||
_removedProperties.RemoveAll(s => s == alias);
|
||||
_addedProperties.RemoveAll(s => s == alias);
|
||||
|
||||
//add to the added props
|
||||
_addedProperties.Add(alias);
|
||||
}
|
||||
else if (e.Action == NotifyCollectionChangedAction.Remove)
|
||||
{
|
||||
var alias = e.OldItems.Cast<IMacroProperty>().Select(x => x.Alias).First();
|
||||
|
||||
//remove from the removed/added props (since people could add/remove all they want in one request)
|
||||
_removedProperties.RemoveAll(s => s == alias);
|
||||
_addedProperties.RemoveAll(s => s == alias);
|
||||
|
||||
//add to the added props
|
||||
_removedProperties.Add(alias);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Used internally to check if we need to add a section in the repository to the db
|
||||
/// </summary>
|
||||
internal IEnumerable<string> AddedProperties
|
||||
{
|
||||
get { return _addedProperties; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Used internally to check if we need to remove a section in the repository to the db
|
||||
/// </summary>
|
||||
internal IEnumerable<string> RemovedProperties
|
||||
{
|
||||
get { return _removedProperties; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the alias of the Macro
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public string Alias
|
||||
{
|
||||
get { return _alias; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_alias = value;
|
||||
return _alias;
|
||||
}, _alias, AliasSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the name of the Macro
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public string Name
|
||||
{
|
||||
get { return _name; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_name = value;
|
||||
return _name;
|
||||
}, _name, NameSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a boolean indicating whether the Macro can be used in an Editor
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public bool UseInEditor
|
||||
{
|
||||
get { return _useInEditor; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_useInEditor = value;
|
||||
return _useInEditor;
|
||||
}, _useInEditor, UseInEditorSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Cache Duration for the Macro
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public int CacheDuration
|
||||
{
|
||||
get { return _cacheDuration; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_cacheDuration = value;
|
||||
return _cacheDuration;
|
||||
}, _cacheDuration, CacheDurationSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a boolean indicating whether the Macro should be Cached by Page
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public bool CacheByPage
|
||||
{
|
||||
get { return _cacheByPage; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_cacheByPage = value;
|
||||
return _cacheByPage;
|
||||
}, _cacheByPage, CacheByPageSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a boolean indicating whether the Macro should be Cached Personally
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public bool CacheByMember
|
||||
{
|
||||
get { return _cacheByMember; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_cacheByMember = value;
|
||||
return _cacheByMember;
|
||||
}, _cacheByMember, CacheByMemberSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a boolean indicating whether the Macro should be rendered in an Editor
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public bool DontRender
|
||||
{
|
||||
get { return _dontRender; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_dontRender = value;
|
||||
return _dontRender;
|
||||
}, _dontRender, DontRenderSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the path to user control or the Control Type to render
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public string ControlType
|
||||
{
|
||||
get { return _scriptFile; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_scriptFile = value;
|
||||
return _scriptFile;
|
||||
}, _scriptFile, ControlPathSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the name of the assembly, which should be used by the Macro
|
||||
/// </summary>
|
||||
/// <remarks>Will usually only be filled if the ControlType is a Usercontrol</remarks>
|
||||
[DataMember]
|
||||
public string ControlAssembly
|
||||
{
|
||||
get { return _scriptAssembly; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_scriptAssembly = value;
|
||||
return _scriptAssembly;
|
||||
}, _scriptAssembly, ControlAssemblySelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or set the path to the Python file in use
|
||||
/// </summary>
|
||||
/// <remarks>Optional: Can only be one of three Script, Python or Xslt</remarks>
|
||||
[DataMember]
|
||||
public string ScriptPath
|
||||
{
|
||||
get { return _python; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_python = value;
|
||||
return _python;
|
||||
}, _python, ScriptPathSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the path to the Xslt file in use
|
||||
/// </summary>
|
||||
/// <remarks>Optional: Can only be one of three Script, Python or Xslt</remarks>
|
||||
[DataMember]
|
||||
public string XsltPath
|
||||
{
|
||||
get { return _xslt; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_xslt = value;
|
||||
return _xslt;
|
||||
}, _xslt, XsltPathSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a list of Macro Properties
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public MacroPropertyCollection Properties
|
||||
{
|
||||
get { return _properties; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns an enum <see cref="MacroTypes"/> based on the properties on the Macro
|
||||
/// </summary>
|
||||
/// <returns><see cref="MacroTypes"/></returns>
|
||||
public MacroTypes MacroType()
|
||||
{
|
||||
if (string.IsNullOrEmpty(XsltPath) == false)
|
||||
return MacroTypes.Xslt;
|
||||
|
||||
if (string.IsNullOrEmpty(ScriptPath) == false)
|
||||
{
|
||||
//we need to check if the file path saved is a virtual path starting with ~/Views/MacroPartials, if so then this is
|
||||
//a partial view macro, not a script macro
|
||||
//we also check if the file exists in ~/App_Plugins/[Packagename]/Views/MacroPartials, if so then it is also a partial view.
|
||||
return (ScriptPath.InvariantStartsWith(SystemDirectories.MvcViews + "/MacroPartials/")
|
||||
|| (Regex.IsMatch(ScriptPath, "~/App_Plugins/.+?/Views/MacroPartials", RegexOptions.Compiled | RegexOptions.IgnoreCase)))
|
||||
? MacroTypes.PartialView
|
||||
: MacroTypes.Script;
|
||||
}
|
||||
|
||||
if (string.IsNullOrEmpty(ControlType) == false && ControlType.InvariantContains(".ascx"))
|
||||
return MacroTypes.UserControl;
|
||||
|
||||
if (string.IsNullOrEmpty(ControlType) == false && string.IsNullOrEmpty(ControlAssembly) == false)
|
||||
return MacroTypes.CustomControl;
|
||||
|
||||
return MacroTypes.Unknown;
|
||||
}
|
||||
}
|
||||
}
|
||||
98
src/Umbraco.Core/Models/MacroProperty.cs
Normal file
98
src/Umbraco.Core/Models/MacroProperty.cs
Normal file
@@ -0,0 +1,98 @@
|
||||
using System;
|
||||
using System.Reflection;
|
||||
using System.Runtime.Serialization;
|
||||
using Umbraco.Core.Models.EntityBase;
|
||||
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents a Macro Property
|
||||
/// </summary>
|
||||
[Serializable]
|
||||
[DataContract(IsReference = true)]
|
||||
internal class MacroProperty : TracksChangesEntityBase, IMacroProperty, IRememberBeingDirty
|
||||
{
|
||||
private string _alias;
|
||||
private string _name;
|
||||
private int _sortOrder;
|
||||
private IMacroPropertyType _propertyType;
|
||||
|
||||
private static readonly PropertyInfo AliasSelector = ExpressionHelper.GetPropertyInfo<MacroProperty, string>(x => x.Alias);
|
||||
private static readonly PropertyInfo NameSelector = ExpressionHelper.GetPropertyInfo<MacroProperty, string>(x => x.Name);
|
||||
private static readonly PropertyInfo SortOrderSelector = ExpressionHelper.GetPropertyInfo<MacroProperty, int>(x => x.SortOrder);
|
||||
private static readonly PropertyInfo PropertyTypeSelector = ExpressionHelper.GetPropertyInfo<MacroProperty, IMacroPropertyType>(x => x.PropertyType);
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Alias of the Property
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public string Alias
|
||||
{
|
||||
get { return _alias; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_alias = value;
|
||||
return _alias;
|
||||
}, _alias, AliasSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Name of the Property
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public string Name
|
||||
{
|
||||
get { return _name; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_name = value;
|
||||
return _name;
|
||||
}, _name, NameSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Sort Order of the Property
|
||||
/// </summary>
|
||||
[DataMember]
|
||||
public int SortOrder
|
||||
{
|
||||
get { return _sortOrder; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_sortOrder = value;
|
||||
return _sortOrder;
|
||||
}, _sortOrder, SortOrderSelector);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the Type for this Property
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// The MacroPropertyTypes acts as a plugin for Macros.
|
||||
/// All types was previously contained in the database, but has been ported to code.
|
||||
/// </remarks>
|
||||
[DataMember]
|
||||
public IMacroPropertyType PropertyType
|
||||
|
||||
{
|
||||
get { return _propertyType; }
|
||||
set
|
||||
{
|
||||
SetPropertyValueAndDetectChanges(o =>
|
||||
{
|
||||
_propertyType = value;
|
||||
return _propertyType;
|
||||
}, _propertyType, PropertyTypeSelector);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
20
src/Umbraco.Core/Models/MacroPropertyCollection.cs
Normal file
20
src/Umbraco.Core/Models/MacroPropertyCollection.cs
Normal file
@@ -0,0 +1,20 @@
|
||||
using System;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// A macro's property collection
|
||||
/// </summary>
|
||||
internal class MacroPropertyCollection : ObservableDictionary<string, IMacroProperty>
|
||||
{
|
||||
public MacroPropertyCollection()
|
||||
: base(property => property.Alias)
|
||||
{
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
20
src/Umbraco.Core/Models/MacroPropertyTypeBaseTypes.cs
Normal file
20
src/Umbraco.Core/Models/MacroPropertyTypeBaseTypes.cs
Normal file
@@ -0,0 +1,20 @@
|
||||
using System;
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// Enum for the three allowed BaseTypes
|
||||
/// </summary>
|
||||
[Serializable]
|
||||
[DataContract(IsReference = true)]
|
||||
internal enum MacroPropertyTypeBaseTypes
|
||||
{
|
||||
[EnumMember]
|
||||
Int32,
|
||||
[EnumMember]
|
||||
Boolean,
|
||||
[EnumMember]
|
||||
String
|
||||
}
|
||||
}
|
||||
28
src/Umbraco.Core/Models/MacroTypes.cs
Normal file
28
src/Umbraco.Core/Models/MacroTypes.cs
Normal file
@@ -0,0 +1,28 @@
|
||||
using System;
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// Enum for the various types of Macros
|
||||
/// </summary>
|
||||
[Serializable]
|
||||
[DataContract(IsReference = true)]
|
||||
internal enum MacroTypes
|
||||
{
|
||||
[EnumMember]
|
||||
Xslt = 1,
|
||||
[EnumMember]
|
||||
CustomControl = 2,
|
||||
[EnumMember]
|
||||
UserControl = 3,
|
||||
[EnumMember]
|
||||
Unknown = 4,
|
||||
[EnumMember]
|
||||
Python = 5,
|
||||
[EnumMember]
|
||||
Script = 6,
|
||||
[EnumMember]
|
||||
PartialView = 7
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
using Umbraco.Core.Persistence;
|
||||
using System.Collections.Generic;
|
||||
using Umbraco.Core.Persistence;
|
||||
using Umbraco.Core.Persistence.DatabaseAnnotations;
|
||||
|
||||
namespace Umbraco.Core.Models.Rdbms
|
||||
@@ -54,5 +55,8 @@ namespace Umbraco.Core.Models.Rdbms
|
||||
[Column("macroPython")]
|
||||
[NullSetting(NullSetting = NullSettings.Null)]
|
||||
public string Python { get; set; }
|
||||
|
||||
[ResultColumn]
|
||||
public List<MacroPropertyDto> MacroPropertyDtos { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -6,100 +6,6 @@ using Umbraco.Core.Sync;
|
||||
|
||||
namespace Umbraco.Core.Models
|
||||
{
|
||||
internal class Macro : Entity, IAggregateRoot
|
||||
{
|
||||
/// <summary>
|
||||
/// Creates an item with pre-filled properties
|
||||
/// </summary>
|
||||
/// <param name="id"></param>
|
||||
/// <param name="useInEditor"></param>
|
||||
/// <param name="refreshRate"></param>
|
||||
/// <param name="alias"></param>
|
||||
/// <param name="name"></param>
|
||||
/// <param name="controlType"></param>
|
||||
/// <param name="controlAssembly"></param>
|
||||
/// <param name="xsltPath"></param>
|
||||
/// <param name="cacheByPage"></param>
|
||||
/// <param name="cachePersonalized"></param>
|
||||
/// <param name="dontRender"></param>
|
||||
/// <param name="scriptPath"></param>
|
||||
public Macro(int id, bool useInEditor, int refreshRate, string @alias, string name, string controlType, string controlAssembly, string xsltPath, bool cacheByPage, bool cachePersonalized, bool dontRender, string scriptPath)
|
||||
{
|
||||
Id = id;
|
||||
UseInEditor = useInEditor;
|
||||
RefreshRate = refreshRate;
|
||||
Alias = alias;
|
||||
Name = name;
|
||||
ControlType = controlType;
|
||||
ControlAssembly = controlAssembly;
|
||||
XsltPath = xsltPath;
|
||||
CacheByPage = cacheByPage;
|
||||
CachePersonalized = cachePersonalized;
|
||||
DontRender = dontRender;
|
||||
ScriptPath = scriptPath;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates an instance for persisting a new item
|
||||
/// </summary>
|
||||
/// <param name="useInEditor"></param>
|
||||
/// <param name="refreshRate"></param>
|
||||
/// <param name="alias"></param>
|
||||
/// <param name="name"></param>
|
||||
/// <param name="controlType"></param>
|
||||
/// <param name="controlAssembly"></param>
|
||||
/// <param name="xsltPath"></param>
|
||||
/// <param name="cacheByPage"></param>
|
||||
/// <param name="cachePersonalized"></param>
|
||||
/// <param name="dontRender"></param>
|
||||
/// <param name="scriptPath"></param>
|
||||
public Macro(string @alias, string name,
|
||||
string controlType = "",
|
||||
string controlAssembly = "",
|
||||
string xsltPath = "",
|
||||
string scriptPath = "",
|
||||
bool cacheByPage = false,
|
||||
bool cachePersonalized = false,
|
||||
bool dontRender = true,
|
||||
bool useInEditor = false,
|
||||
int refreshRate = 0)
|
||||
{
|
||||
UseInEditor = useInEditor;
|
||||
RefreshRate = refreshRate;
|
||||
Alias = alias;
|
||||
Name = name;
|
||||
ControlType = controlType;
|
||||
ControlAssembly = controlAssembly;
|
||||
XsltPath = xsltPath;
|
||||
CacheByPage = cacheByPage;
|
||||
CachePersonalized = cachePersonalized;
|
||||
DontRender = dontRender;
|
||||
ScriptPath = scriptPath;
|
||||
}
|
||||
|
||||
public bool UseInEditor { get; set; }
|
||||
|
||||
public int RefreshRate { get; set; }
|
||||
|
||||
public string Alias { get; set; }
|
||||
|
||||
public string Name { get; set; }
|
||||
|
||||
public string ControlType { get; set; }
|
||||
|
||||
public string ControlAssembly { get; set; }
|
||||
|
||||
public string XsltPath { get; set; }
|
||||
|
||||
public bool CacheByPage { get; set; }
|
||||
|
||||
public bool CachePersonalized { get; set; }
|
||||
|
||||
public bool DontRender { get; set; }
|
||||
|
||||
public string ScriptPath { get; set; }
|
||||
}
|
||||
|
||||
internal class ServerRegistration : Entity, IServerAddress, IAggregateRoot
|
||||
{
|
||||
private string _serverAddress;
|
||||
|
||||
150
src/Umbraco.Core/ObservableDictionary.cs
Normal file
150
src/Umbraco.Core/ObservableDictionary.cs
Normal file
@@ -0,0 +1,150 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Umbraco.Core
|
||||
{
|
||||
/// <summary>
|
||||
/// An ObservableDictionary
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// Assumes that the key will not change and is unique for each element in the collection.
|
||||
/// Collection is not thread-safe, so calls should be made single-threaded.
|
||||
/// </remarks>
|
||||
/// <typeparam name="TValue">The type of elements contained in the BindableCollection</typeparam>
|
||||
/// <typeparam name="TKey">The type of the indexing key</typeparam>
|
||||
internal class ObservableDictionary<TKey, TValue> : ObservableCollection<TValue>
|
||||
{
|
||||
protected Dictionary<TKey, int> Indecies = new Dictionary<TKey, int>();
|
||||
protected Func<TValue, TKey> KeySelector;
|
||||
|
||||
/// <summary>
|
||||
/// Create new ObservableDictionary
|
||||
/// </summary>
|
||||
/// <param name="keySelector">Selector function to create key from value</param>
|
||||
public ObservableDictionary(Func<TValue, TKey> keySelector)
|
||||
: base()
|
||||
{
|
||||
if (keySelector == null) throw new ArgumentException("keySelector");
|
||||
KeySelector = keySelector;
|
||||
}
|
||||
|
||||
#region Protected Methods
|
||||
protected override void InsertItem(int index, TValue item)
|
||||
{
|
||||
var key = KeySelector(item);
|
||||
if (Indecies.ContainsKey(key))
|
||||
throw new DuplicateKeyException(key.ToString());
|
||||
|
||||
if (index != this.Count)
|
||||
{
|
||||
foreach (var k in Indecies.Keys.Where(k => Indecies[k] >= index).ToList())
|
||||
{
|
||||
Indecies[k]++;
|
||||
}
|
||||
}
|
||||
|
||||
base.InsertItem(index, item);
|
||||
Indecies[key] = index;
|
||||
|
||||
}
|
||||
|
||||
protected override void ClearItems()
|
||||
{
|
||||
base.ClearItems();
|
||||
Indecies.Clear();
|
||||
}
|
||||
|
||||
|
||||
protected override void RemoveItem(int index)
|
||||
{
|
||||
var item = this[index];
|
||||
var key = KeySelector(item);
|
||||
|
||||
base.RemoveItem(index);
|
||||
|
||||
Indecies.Remove(key);
|
||||
|
||||
foreach (var k in Indecies.Keys.Where(k => Indecies[k] > index).ToList())
|
||||
{
|
||||
Indecies[k]--;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
public virtual bool ContainsKey(TKey key)
|
||||
{
|
||||
return Indecies.ContainsKey(key);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the element with the specified key. If setting a new value, new value must have same key.
|
||||
/// </summary>
|
||||
/// <param name="key">Key of element to replace</param>
|
||||
/// <returns></returns>
|
||||
public virtual TValue this[TKey key]
|
||||
{
|
||||
|
||||
get { return this[Indecies[key]]; }
|
||||
set
|
||||
{
|
||||
//confirm key matches
|
||||
if (!KeySelector(value).Equals(key))
|
||||
throw new InvalidOperationException("Key of new value does not match");
|
||||
|
||||
if (!Indecies.ContainsKey(key))
|
||||
{
|
||||
this.Add(value);
|
||||
}
|
||||
else
|
||||
{
|
||||
this[Indecies[key]] = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Replaces element at given key with new value. New value must have same key.
|
||||
/// </summary>
|
||||
/// <param name="key">Key of element to replace</param>
|
||||
/// <param name="value">New value</param>
|
||||
///
|
||||
/// <exception cref="InvalidOperationException"></exception>
|
||||
/// <returns>False if key not found</returns>
|
||||
public virtual bool Replace(TKey key, TValue value)
|
||||
{
|
||||
if (!Indecies.ContainsKey(key)) return false;
|
||||
//confirm key matches
|
||||
if (!KeySelector(value).Equals(key))
|
||||
throw new InvalidOperationException("Key of new value does not match");
|
||||
|
||||
this[Indecies[key]] = value;
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
public virtual bool Remove(TKey key)
|
||||
{
|
||||
if (!Indecies.ContainsKey(key)) return false;
|
||||
|
||||
this.RemoveAt(Indecies[key]);
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
internal class DuplicateKeyException : Exception
|
||||
{
|
||||
|
||||
public string Key { get; private set; }
|
||||
public DuplicateKeyException(string key)
|
||||
: base("Attempted to insert duplicate key " + key + " in collection")
|
||||
{
|
||||
Key = key;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -4,11 +4,11 @@ using Umbraco.Core.Models.Rdbms;
|
||||
|
||||
namespace Umbraco.Core.Persistence.Factories
|
||||
{
|
||||
internal class MacroFactory : IEntityFactory<Macro, MacroDto>
|
||||
internal class MacroFactory : IEntityFactory<IMacro, MacroDto>
|
||||
{
|
||||
#region Implementation of IEntityFactory<Language,LanguageDto>
|
||||
|
||||
public Macro BuildEntity(MacroDto dto)
|
||||
public IMacro BuildEntity(MacroDto dto)
|
||||
{
|
||||
var model = new Macro(dto.Id, dto.UseInEditor, dto.RefreshRate, dto.Alias, dto.Name, dto.ScriptType, dto.ScriptAssembly, dto.Xslt, dto.CacheByPage, dto.CachePersonalized, dto.DontRender, dto.Python);
|
||||
//on initial construction we don't want to have dirty properties tracked
|
||||
@@ -17,17 +17,17 @@ namespace Umbraco.Core.Persistence.Factories
|
||||
return model;
|
||||
}
|
||||
|
||||
public MacroDto BuildDto(Macro entity)
|
||||
public MacroDto BuildDto(IMacro entity)
|
||||
{
|
||||
var dto = new MacroDto()
|
||||
{
|
||||
Alias = entity.Alias,
|
||||
CacheByPage = entity.CacheByPage,
|
||||
CachePersonalized = entity.CachePersonalized,
|
||||
CachePersonalized = entity.CacheByMember,
|
||||
DontRender = entity.DontRender,
|
||||
Name = entity.Name,
|
||||
Python = entity.ScriptPath,
|
||||
RefreshRate = entity.RefreshRate,
|
||||
RefreshRate = entity.CacheDuration,
|
||||
ScriptAssembly = entity.ControlAssembly,
|
||||
ScriptType = entity.ControlType,
|
||||
UseInEditor = entity.UseInEditor,
|
||||
|
||||
@@ -5,6 +5,7 @@ using Umbraco.Core.Models.Rdbms;
|
||||
namespace Umbraco.Core.Persistence.Mappers
|
||||
{
|
||||
[MapperFor(typeof(Macro))]
|
||||
[MapperFor(typeof(IMacro))]
|
||||
internal sealed class MacroMapper : BaseMapper
|
||||
{
|
||||
private static readonly ConcurrentDictionary<string, DtoMapModel> PropertyInfoCacheInstance = new ConcurrentDictionary<string, DtoMapModel>();
|
||||
@@ -28,12 +29,12 @@ namespace Umbraco.Core.Persistence.Mappers
|
||||
CacheMap<Macro, MacroDto>(src => src.Id, dto => dto.Id);
|
||||
CacheMap<Macro, MacroDto>(src => src.Alias, dto => dto.Alias);
|
||||
CacheMap<Macro, MacroDto>(src => src.CacheByPage, dto => dto.CacheByPage);
|
||||
CacheMap<Macro, MacroDto>(src => src.CachePersonalized, dto => dto.CachePersonalized);
|
||||
CacheMap<Macro, MacroDto>(src => src.CacheByMember, dto => dto.CachePersonalized);
|
||||
CacheMap<Macro, MacroDto>(src => src.ControlAssembly, dto => dto.ScriptAssembly);
|
||||
CacheMap<Macro, MacroDto>(src => src.ControlType, dto => dto.ScriptType);
|
||||
CacheMap<Macro, MacroDto>(src => src.DontRender, dto => dto.DontRender);
|
||||
CacheMap<Macro, MacroDto>(src => src.Name, dto => dto.Name);
|
||||
CacheMap<Macro, MacroDto>(src => src.RefreshRate, dto => dto.RefreshRate);
|
||||
CacheMap<Macro, MacroDto>(src => src.CacheDuration, dto => dto.RefreshRate);
|
||||
CacheMap<Macro, MacroDto>(src => src.ScriptPath, dto => dto.Python);
|
||||
CacheMap<Macro, MacroDto>(src => src.UseInEditor, dto => dto.UseInEditor);
|
||||
CacheMap<Macro, MacroDto>(src => src.XsltPath, dto => dto.Xslt);
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
using Umbraco.Core.Models;
|
||||
|
||||
namespace Umbraco.Core.Persistence.Repositories
|
||||
{
|
||||
internal interface IMacroRepository : IRepositoryQueryable<int, IMacro>
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
@@ -7,11 +7,12 @@ using Umbraco.Core.Models.Rdbms;
|
||||
using Umbraco.Core.Persistence.Caching;
|
||||
using Umbraco.Core.Persistence.Factories;
|
||||
using Umbraco.Core.Persistence.Querying;
|
||||
using Umbraco.Core.Persistence.SqlSyntax;
|
||||
using Umbraco.Core.Persistence.UnitOfWork;
|
||||
|
||||
namespace Umbraco.Core.Persistence.Repositories
|
||||
{
|
||||
internal class MacroRepository : PetaPocoRepositoryBase<int, Macro>
|
||||
internal class MacroRepository : PetaPocoRepositoryBase<int, IMacro>, IMacroRepository
|
||||
{
|
||||
public MacroRepository(IDatabaseUnitOfWork work) : base(work)
|
||||
{
|
||||
@@ -21,7 +22,7 @@ namespace Umbraco.Core.Persistence.Repositories
|
||||
{
|
||||
}
|
||||
|
||||
protected override Macro PerformGet(int id)
|
||||
protected override IMacro PerformGet(int id)
|
||||
{
|
||||
var sql = GetBaseQuery(false);
|
||||
sql.Where(GetBaseWhereClause(), new { Id = id });
|
||||
@@ -35,12 +36,12 @@ namespace Umbraco.Core.Persistence.Repositories
|
||||
|
||||
//on initial construction we don't want to have dirty properties tracked
|
||||
// http://issues.umbraco.org/issue/U4-1946
|
||||
entity.ResetDirtyProperties(false);
|
||||
((TracksChangesEntityBase)entity).ResetDirtyProperties(false);
|
||||
|
||||
return entity;
|
||||
}
|
||||
|
||||
protected override IEnumerable<Macro> PerformGetAll(params int[] ids)
|
||||
protected override IEnumerable<IMacro> PerformGetAll(params int[] ids)
|
||||
{
|
||||
if (ids.Any())
|
||||
{
|
||||
@@ -59,10 +60,10 @@ namespace Umbraco.Core.Persistence.Repositories
|
||||
}
|
||||
}
|
||||
|
||||
protected override IEnumerable<Macro> PerformGetByQuery(IQuery<Macro> query)
|
||||
protected override IEnumerable<IMacro> PerformGetByQuery(IQuery<IMacro> query)
|
||||
{
|
||||
var sqlClause = GetBaseQuery(false);
|
||||
var translator = new SqlTranslator<Macro>(sqlClause, query);
|
||||
var translator = new SqlTranslator<IMacro>(sqlClause, query);
|
||||
var sql = translator.Translate();
|
||||
|
||||
var dtos = Database.Fetch<Macro>(sql);
|
||||
@@ -76,8 +77,24 @@ namespace Umbraco.Core.Persistence.Repositories
|
||||
protected override Sql GetBaseQuery(bool isCount)
|
||||
{
|
||||
var sql = new Sql();
|
||||
sql.Select(isCount ? "COUNT(*)" : "*")
|
||||
.From<MacroDto>();
|
||||
if (isCount)
|
||||
{
|
||||
sql.Select("COUNT(*)").From<MacroDto>();
|
||||
}
|
||||
else
|
||||
{
|
||||
return GetBaseQuery("*");
|
||||
}
|
||||
return sql;
|
||||
}
|
||||
|
||||
private static Sql GetBaseQuery(string columns)
|
||||
{
|
||||
var sql = new Sql();
|
||||
sql.Select(columns)
|
||||
.From<MacroDto>()
|
||||
.LeftJoin<MacroPropertyDto>()
|
||||
.On<MacroDto, MacroPropertyDto>(left => left.Id, right => right.Macro);
|
||||
return sql;
|
||||
}
|
||||
|
||||
@@ -100,7 +117,7 @@ namespace Umbraco.Core.Persistence.Repositories
|
||||
get { throw new NotImplementedException(); }
|
||||
}
|
||||
|
||||
protected override void PersistNewItem(Macro entity)
|
||||
protected override void PersistNewItem(IMacro entity)
|
||||
{
|
||||
((Entity)entity).AddingEntity();
|
||||
|
||||
@@ -110,10 +127,17 @@ namespace Umbraco.Core.Persistence.Repositories
|
||||
var id = Convert.ToInt32(Database.Insert(dto));
|
||||
entity.Id = id;
|
||||
|
||||
foreach (var propDto in dto.MacroPropertyDtos)
|
||||
{
|
||||
//need to set the id explicitly here
|
||||
propDto.Macro = id;
|
||||
Database.Insert(propDto);
|
||||
}
|
||||
|
||||
((ICanBeDirty)entity).ResetDirtyProperties();
|
||||
}
|
||||
|
||||
protected override void PersistUpdatedItem(Macro entity)
|
||||
protected override void PersistUpdatedItem(IMacro entity)
|
||||
{
|
||||
((Entity)entity).UpdatingEntity();
|
||||
|
||||
@@ -122,6 +146,33 @@ namespace Umbraco.Core.Persistence.Repositories
|
||||
|
||||
Database.Update(dto);
|
||||
|
||||
//update the sections if they've changed
|
||||
var macro = (Macro)entity;
|
||||
if (macro.IsPropertyDirty("Properties"))
|
||||
{
|
||||
//for any that exist on the object, we need to determine if we need to update or insert
|
||||
foreach (var propDto in dto.MacroPropertyDtos)
|
||||
{
|
||||
if (macro.AddedProperties.Contains(propDto.Alias))
|
||||
{
|
||||
//we need to insert since this was added
|
||||
Database.Insert(propDto);
|
||||
}
|
||||
else
|
||||
{
|
||||
Database.Update(propDto);
|
||||
}
|
||||
}
|
||||
|
||||
//now we need to delete any props that have been removed
|
||||
foreach (var propAlias in macro.RemovedProperties)
|
||||
{
|
||||
//delete the property
|
||||
Database.Delete<MacroPropertyDto>("WHERE macro=@macroId AND macroPropertyAlias=@propAlias",
|
||||
new { macroId = macro.Id, propAlias = propAlias });
|
||||
}
|
||||
}
|
||||
|
||||
((ICanBeDirty)entity).ResetDirtyProperties();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -315,6 +315,14 @@
|
||||
<Compile Include="Models\IDictionaryTranslation.cs" />
|
||||
<Compile Include="Models\IFile.cs" />
|
||||
<Compile Include="Models\ILanguage.cs" />
|
||||
<Compile Include="Models\IMacro.cs" />
|
||||
<Compile Include="Models\IMacroProperty.cs" />
|
||||
<Compile Include="Models\IMacroPropertyType.cs" />
|
||||
<Compile Include="Models\Macro.cs" />
|
||||
<Compile Include="Models\MacroProperty.cs" />
|
||||
<Compile Include="Models\MacroPropertyCollection.cs" />
|
||||
<Compile Include="Models\MacroPropertyTypeBaseTypes.cs" />
|
||||
<Compile Include="Models\MacroTypes.cs" />
|
||||
<Compile Include="Models\Mapping\IMapperConfiguration.cs" />
|
||||
<Compile Include="Models\Mapping\MapperConfiguration.cs" />
|
||||
<Compile Include="Models\Membership\EntityPermission.cs" />
|
||||
@@ -370,6 +378,7 @@
|
||||
<Compile Include="Models\Validation\RequiredForPersistenceAttribute.cs" />
|
||||
<Compile Include="ObjectResolution\ApplicationEventsResolver.cs" />
|
||||
<Compile Include="ObjectResolution\ResolverCollection.cs" />
|
||||
<Compile Include="ObservableDictionary.cs" />
|
||||
<Compile Include="Persistence\Caching\InMemoryCacheProvider.cs" />
|
||||
<Compile Include="Persistence\Caching\IRepositoryCacheProvider.cs" />
|
||||
<Compile Include="Persistence\Caching\NullCacheProvider.cs" />
|
||||
@@ -398,6 +407,7 @@
|
||||
<Compile Include="Persistence\Mappers\MacroMapper.cs" />
|
||||
<Compile Include="Persistence\Migrations\Upgrades\TargetVersionSeven\RemoveDefaultPermissionUserColumn.cs" />
|
||||
<Compile Include="Persistence\Migrations\Upgrades\TargetVersionSeven\UpdateControlIdToPropertyEditorAlias.cs" />
|
||||
<Compile Include="Persistence\Repositories\Interfaces\IMacroRepository.cs" />
|
||||
<Compile Include="Persistence\Repositories\MacroRepository.cs" />
|
||||
<Compile Include="PropertyEditors\LegacyPropertyEditorIdToAliasConverter.cs" />
|
||||
<Compile Include="Persistence\Mappers\MapperForAttribute.cs" />
|
||||
|
||||
@@ -88,12 +88,12 @@ namespace Umbraco.Tests.Persistence.Repositories
|
||||
Assert.That(macro.HasIdentity, Is.True);
|
||||
Assert.That(macro.Alias, Is.EqualTo("test1"));
|
||||
Assert.That(macro.CacheByPage, Is.EqualTo(false));
|
||||
Assert.That(macro.CachePersonalized, Is.EqualTo(false));
|
||||
Assert.That(macro.CacheByMember, Is.EqualTo(false));
|
||||
Assert.That(macro.ControlAssembly, Is.EqualTo("MyAssembly1"));
|
||||
Assert.That(macro.ControlType, Is.EqualTo("~/usercontrol/test1.ascx"));
|
||||
Assert.That(macro.DontRender, Is.EqualTo(true));
|
||||
Assert.That(macro.Name, Is.EqualTo("Test1"));
|
||||
Assert.That(macro.RefreshRate, Is.EqualTo(0));
|
||||
Assert.That(macro.CacheDuration, Is.EqualTo(0));
|
||||
Assert.That(macro.ScriptPath, Is.EqualTo("~/views/macropartials/test1.cshtml"));
|
||||
Assert.That(macro.UseInEditor, Is.EqualTo(false));
|
||||
Assert.That(macro.XsltPath, Is.EqualTo("test1.xslt"));
|
||||
@@ -128,7 +128,7 @@ namespace Umbraco.Tests.Persistence.Repositories
|
||||
using (var repository = new MacroRepository(unitOfWork))
|
||||
{
|
||||
// Act
|
||||
var query = Query<Macro>.Builder.Where(x => x.Alias.ToUpper() == "TEST1");
|
||||
var query = Query<IMacro>.Builder.Where(x => x.Alias.ToUpper() == "TEST1");
|
||||
var result = repository.GetByQuery(query);
|
||||
|
||||
// Assert
|
||||
@@ -145,7 +145,7 @@ namespace Umbraco.Tests.Persistence.Repositories
|
||||
using (var repository = new MacroRepository(unitOfWork))
|
||||
{
|
||||
// Act
|
||||
var query = Query<Macro>.Builder.Where(x => x.Name.StartsWith("Test"));
|
||||
var query = Query<IMacro>.Builder.Where(x => x.Name.StartsWith("Test"));
|
||||
int count = repository.Count(query);
|
||||
|
||||
// Assert
|
||||
@@ -183,9 +183,9 @@ namespace Umbraco.Tests.Persistence.Repositories
|
||||
// Act
|
||||
var macro = repository.Get(2);
|
||||
macro.Name = "Hello";
|
||||
macro.RefreshRate = 1234;
|
||||
macro.CacheDuration = 1234;
|
||||
macro.CacheByPage = true;
|
||||
macro.CachePersonalized = true;
|
||||
macro.CacheByMember = true;
|
||||
macro.ControlAssembly = "";
|
||||
macro.ControlType = "";
|
||||
macro.DontRender = false;
|
||||
@@ -201,9 +201,9 @@ namespace Umbraco.Tests.Persistence.Repositories
|
||||
// Assert
|
||||
Assert.That(macroUpdated, Is.Not.Null);
|
||||
Assert.That(macroUpdated.Name, Is.EqualTo("Hello"));
|
||||
Assert.That(macroUpdated.RefreshRate, Is.EqualTo(1234));
|
||||
Assert.That(macroUpdated.CacheDuration, Is.EqualTo(1234));
|
||||
Assert.That(macroUpdated.CacheByPage, Is.EqualTo(true));
|
||||
Assert.That(macroUpdated.CachePersonalized, Is.EqualTo(true));
|
||||
Assert.That(macroUpdated.CacheByMember, Is.EqualTo(true));
|
||||
Assert.That(macroUpdated.ControlAssembly, Is.EqualTo(""));
|
||||
Assert.That(macroUpdated.ControlType, Is.EqualTo(""));
|
||||
Assert.That(macroUpdated.DontRender, Is.EqualTo(false));
|
||||
@@ -266,7 +266,7 @@ namespace Umbraco.Tests.Persistence.Repositories
|
||||
{
|
||||
repository.AddOrUpdate(new Macro("test1", "Test1", "~/usercontrol/test1.ascx", "MyAssembly1", "test1.xslt", "~/views/macropartials/test1.cshtml"));
|
||||
repository.AddOrUpdate(new Macro("test2", "Test2", "~/usercontrol/test2.ascx", "MyAssembly2", "test2.xslt", "~/views/macropartials/test2.cshtml"));
|
||||
repository.AddOrUpdate(new Macro("test3", "Test3", "~/usercontrol/test3.ascx", "MyAssembly3", "test3.xslt", "~/views/macropartials/test3.cshtml"));
|
||||
repository.AddOrUpdate(new Macro("test3", "Tet3", "~/usercontrol/test3.ascx", "MyAssembly3", "test3.xslt", "~/views/macropartials/test3.cshtml"));
|
||||
unitOfWork.Commit();
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user