diff --git a/build/NuSpecs/UmbracoCms.Web.nuspec b/build/NuSpecs/UmbracoCms.Web.nuspec index 7199f414b1..969ac5be3d 100644 --- a/build/NuSpecs/UmbracoCms.Web.nuspec +++ b/build/NuSpecs/UmbracoCms.Web.nuspec @@ -25,7 +25,7 @@ not want this to happen as the alpha of the next major is, really, the next major already. --> - + diff --git a/src/Umbraco.Infrastructure/Models/Property.cs b/src/Umbraco.Infrastructure/Models/Property.cs index 36efbad404..89875811bd 100644 --- a/src/Umbraco.Infrastructure/Models/Property.cs +++ b/src/Umbraco.Infrastructure/Models/Property.cs @@ -98,7 +98,7 @@ namespace Umbraco.Core.Models /// /// Represents a property value. /// - public class PropertyValue : IPropertyValue + public class PropertyValue : IPropertyValue, IEquatable { // TODO: Either we allow change tracking at this class level, or we add some special change tracking collections to the Property // class to deal with change tracking which variants have changed @@ -143,6 +143,27 @@ namespace Umbraco.Core.Models /// public IPropertyValue Clone() => new PropertyValue { _culture = _culture, _segment = _segment, PublishedValue = PublishedValue, EditedValue = EditedValue }; + + + public override bool Equals(object obj) + { + return Equals(obj as PropertyValue); + } + + public bool Equals(PropertyValue other) + { + return other != null && + _culture == other._culture && + _segment == other._segment; + } + + public override int GetHashCode() + { + var hashCode = -1254204277; + hashCode = hashCode * -1521134295 + EqualityComparer.Default.GetHashCode(_culture); + hashCode = hashCode * -1521134295 + EqualityComparer.Default.GetHashCode(_segment); + return hashCode; + } } private static readonly DelegateEqualityComparer PropertyValueComparer = new DelegateEqualityComparer( @@ -508,6 +529,19 @@ namespace Umbraco.Core.Models var clonedEntity = (Property)clone; + //manually clone _values, _pvalue, _vvalues + clonedEntity._values = _values?.Select(x => x.Clone()).ToList(); // all values get copied + clonedEntity._pvalue = _pvalue?.Clone(); + // the tricky part here is that _values contains ALL values including the values in the _vvalues + // dictionary and they are by reference which is why we have equality overloads on PropertyValue + if (clonedEntity._vvalues != null) + { + clonedEntity._vvalues = new Dictionary(); + foreach (var item in _vvalues) + { + clonedEntity._vvalues[item.Key] = clonedEntity._values.First(x => x.Equals(item.Value)); + } + } //need to manually assign since this is a readonly property clonedEntity.PropertyType = (PropertyType) PropertyType.DeepClone(); } diff --git a/src/Umbraco.Tests/Services/ContentServiceTests.cs b/src/Umbraco.Tests/Services/ContentServiceTests.cs index fa47f085c9..79a2832822 100644 --- a/src/Umbraco.Tests/Services/ContentServiceTests.cs +++ b/src/Umbraco.Tests/Services/ContentServiceTests.cs @@ -1890,6 +1890,49 @@ namespace Umbraco.Tests.Services //Assert.AreNotEqual(content.Name, copy.Name); } + [Test] + public void Can_Copy_And_Modify_Content_With_Events() + { + // see https://github.com/umbraco/Umbraco-CMS/issues/5513 + + TypedEventHandler> copying = (sender, args) => + { + args.Copy.SetValue("title", "1"); + args.Original.SetValue("title", "2"); + }; + + TypedEventHandler> copied = (sender, args) => + { + var copyVal = args.Copy.GetValue("title"); + var origVal = args.Original.GetValue("title"); + + Assert.AreEqual("1", copyVal); + Assert.AreEqual("2", origVal); + }; + + try + { + var contentService = ServiceContext.ContentService; + + ContentService.Copying += copying; + ContentService.Copied += copied; + + var contentType = MockedContentTypes.CreateSimpleContentType(); + ServiceContext.ContentTypeService.Save(contentType); + var content = MockedContent.CreateSimpleContent(contentType); + content.SetValue("title", "New Value"); + contentService.Save(content); + + var copy = contentService.Copy(content, content.ParentId, false, Constants.Security.SuperUserId); + Assert.AreEqual("1", copy.GetValue("title")); + } + finally + { + ContentService.Copying -= copying; + ContentService.Copied -= copied; + } + } + [Test] public void Can_Copy_Recursive() { diff --git a/src/Umbraco.Web.UI/Umbraco.Web.UI.csproj b/src/Umbraco.Web.UI/Umbraco.Web.UI.csproj index 1087cce531..fe11a8d9aa 100644 --- a/src/Umbraco.Web.UI/Umbraco.Web.UI.csproj +++ b/src/Umbraco.Web.UI/Umbraco.Web.UI.csproj @@ -84,7 +84,7 @@ - + diff --git a/src/Umbraco.Web/Umbraco.Web.csproj b/src/Umbraco.Web/Umbraco.Web.csproj index 634e27fcda..0e1c5047b3 100755 --- a/src/Umbraco.Web/Umbraco.Web.csproj +++ b/src/Umbraco.Web/Umbraco.Web.csproj @@ -67,6 +67,9 @@ 2.0.0-alpha.20200128.15 + + + 2.7.0.100