Files
Umbraco-CMS/tests/Umbraco.Tests.Common/Builders/ContentDataBuilder.cs

216 lines
7.2 KiB
C#
Raw Normal View History

using Umbraco.Cms.Core.Models;
using Umbraco.Cms.Core.Strings;
V15: Remove Nucache (#17166) * Remove nucache reference from Web.Common * Get tests building-ish * Move ReservedFieldNamesService to the right project * Remove IPublishedSnapshotStatus * Added functionality to the INavigationQueryService to get root keys * Fixed issue with navigation * Remove IPublishedSnapshot from UmbracoContext * Begin removing usage of IPublishedSnapshot from PublishedContentExtensions * Fix PublishedContentExtensions.cs * Don't use snapshots in delivery media api * Use IPublishedMediaCache in QueryMediaApiController * Remove more usages of IPublishedSnapshotAccessor * Comment out tests * Remove more usages of PublishedSnapshotAccessor * Remove PublishedSnapshot from property * Fixed test build * Fix errors * Fix some tests * Delete NuCache 🎉 * Implement DatabaseCacheRebuilder * Remove usage of IPublishedSnapshotService * Remove IPublishedSnapshotService * Remove TestPublishedSnapshotAccessor and make tests build * Don't test Snapshot cachelevel It's no longer supported * Fix BlockEditorConverter Element != Element document type * Remember to set cachemanager * Fix RichTextParserTests * Implement TryGetLevel on INavigationQueryService * Fake level and obsolete it in PublishedContent * Remove ChildrenForAllCultures * Hack Path property on PublishedContent * Remove usages of IPublishedSnapshot in tests * More ConvertersTests * Add hybrid cache to integration tests We can actually do this now because we no longer save files on disk * Rename IPublishedSnapshotRebuilder to ICacheRebuilder * Comment out tests * V15: Replacing the usages of Parent (navigation data) from IPublishedContent (#17125) * Fix .Parent references in PublishedContentExtensions * Add missing methods to FriendlyPublishedContentExtensions (ones that you were able to call on the content directly as they now require extra params) * Fix references from the extension methods * Fix dependencies in tests * Replace IPublishedSnapshotAccessor with the content cache in tests * Resolving more .Parent references * Fix unit tests * Obsolete and use extension methods * Remove private method and use extension instead * Moving code around * Fix tests * Fix more references * Cleanup * Fix more usages * Resolve merge conflict * Fix tests * Cleanup * Fix more tests * Fixed unit tests * Cleanup * Replace last usages --------- Co-authored-by: Bjarke Berg <mail@bergmania.dk> * Remove usage of IPublishedSnapshotAccessor from IRequestItemProvider * Post merge fixup * Remo IPublishedSnapshot * Add HasAny to IDocumentUrlService * Fix TextBuilder * Fix modelsbuilder tests * Use explicit types * Implement GetByContentType * Support element types in PublishedContentTypeCache * Run enlistments before publishing notifications * Fix elements cache refreshing * Implement GetByUdi * Implement GetAtRoot * Implement GetByRoute * Reimplement GetRouteById * Fix blocks unit tests * Initialize domain cache on boot * Only return routes with domains on non default lanauges * V15: Replacing the usages of `Children` (navigation data) from `IPublishedContent` (#17159) * Update params in PublishedContentExtensions to the general interfaces for the published cache and navigation service, so that we can use the extension methods on both documents and media * Introduce GetParent() which uses the right services * Fix obsolete message on .Parent * Obsolete .Children * Fix usages of Children for ApiMediaQueryService * Fix usage in internal * Fix usages in views * Fix indentation * Fix issue with delete language * Update nuget pacakges * Clear elements cache when content is deleted instead of trying to update it * Reset publishedModelFactory * Fixed publishing --------- Co-authored-by: Bjarke Berg <mail@bergmania.dk> Co-authored-by: Elitsa Marinovska <21998037+elit0451@users.noreply.github.com> Co-authored-by: kjac <kja@umbraco.dk>
2024-10-01 15:03:02 +02:00
using Umbraco.Cms.Infrastructure.HybridCache;
using Umbraco.Cms.Tests.Common.Builders.Extensions;
using Umbraco.Cms.Tests.Common.Builders.Interfaces;
using Umbraco.Extensions;
namespace Umbraco.Cms.Tests.Common.Builders;
internal sealed class ContentDataBuilder : BuilderBase<ContentData>, IWithNameBuilder
{
private Dictionary<string, CultureVariation> _cultureInfos;
private string _name;
private DateTime? _now;
private Dictionary<string, PropertyData[]> _properties;
private bool? _published;
private string _segment;
private int? _templateId;
private int? _versionId;
private int? _writerId;
string IWithNameBuilder.Name
{
get => _name;
set => _name = value;
}
public ContentDataBuilder WithVersionDate(DateTime now)
{
_now = now;
return this;
}
public ContentDataBuilder WithUrlSegment(string segment)
{
_segment = segment;
return this;
}
public ContentDataBuilder WithVersionId(int versionId)
{
_versionId = versionId;
return this;
}
public ContentDataBuilder WithWriterId(int writerId)
{
_writerId = writerId;
return this;
}
public ContentDataBuilder WithTemplateId(int templateId)
{
_templateId = templateId;
return this;
}
public ContentDataBuilder WithPublished(bool published)
{
_published = published;
return this;
}
public ContentDataBuilder WithProperties(Dictionary<string, PropertyData[]> properties)
{
_properties = properties;
return this;
}
public ContentDataBuilder WithCultureInfos(Dictionary<string, CultureVariation> cultureInfos)
{
_cultureInfos = cultureInfos;
return this;
}
/// <summary>
/// Build and dynamically update an existing content type
/// </summary>
/// <typeparam name="TContentType"></typeparam>
/// <param name="shortStringHelper"></param>
/// <param name="propertyDataTypes"></param>
/// <param name="contentType"></param>
/// <param name="contentTypeAlias">
/// Will configure the content type with this alias/name if supplied when it's not already set on the content type.
/// </param>
/// <param name="autoCreateCultureNames"></param>
/// <returns></returns>
public ContentData Build<TContentType>(
IShortStringHelper shortStringHelper,
Dictionary<string, IDataType> propertyDataTypes,
TContentType contentType,
string contentTypeAlias = null,
bool autoCreateCultureNames = false) where TContentType : class, IContentTypeComposition
{
if (_name.IsNullOrWhiteSpace())
{
throw new InvalidOperationException("Cannot build without a name");
}
_segment ??= _name.ToLower().ReplaceNonAlphanumericChars('-');
// create or copy the current culture infos for the content
var contentCultureInfos = _cultureInfos == null
? new Dictionary<string, CultureVariation>()
: new Dictionary<string, CultureVariation>(_cultureInfos);
contentType.Alias ??= contentTypeAlias;
contentType.Name ??= contentTypeAlias;
contentType.Key = contentType.Key == default ? Guid.NewGuid() : contentType.Key;
contentType.Id = contentType.Id == default ? Math.Abs(contentTypeAlias.GetHashCode()) : contentType.Id;
if (_properties == null)
{
_properties = new Dictionary<string, PropertyData[]>();
}
foreach (var prop in _properties)
{
//var dataType = new DataType(new VoidEditor("Label", Mock.Of<IDataValueEditorFactory>()), new ConfigurationEditorJsonSerializer())
//{
// Id = 4
//};
if (!propertyDataTypes.TryGetValue(prop.Key, out var dataType))
{
dataType = propertyDataTypes.First().Value;
}
var propertyType = new PropertyType(shortStringHelper, dataType, prop.Key);
// check each property for culture and set variations accordingly,
// this will also ensure that we have the correct culture name on the content
// set for each culture too.
foreach (var cultureValue in prop.Value.Where(x => !x.Culture.IsNullOrWhiteSpace()))
{
// set the property type to vary based on the values
propertyType.Variations |= ContentVariation.Culture;
// if there isn't already a culture, then add one with the default name
if (autoCreateCultureNames &&
!contentCultureInfos.TryGetValue(cultureValue.Culture, out var cultureVariation))
{
cultureVariation = new CultureVariation
{
Date = DateTime.Now,
IsDraft = true,
Name = _name,
UrlSegment = _segment
};
contentCultureInfos[cultureValue.Culture] = cultureVariation;
}
}
// set variations for segments if there is any
if (prop.Value.Any(x => !x.Segment.IsNullOrWhiteSpace()))
{
propertyType.Variations |= ContentVariation.Segment;
contentType.Variations |= ContentVariation.Segment;
}
if (!contentType.PropertyTypeExists(propertyType.Alias))
{
contentType.AddPropertyType(propertyType);
}
}
if (contentCultureInfos.Count > 0)
{
contentType.Variations |= ContentVariation.Culture;
WithCultureInfos(contentCultureInfos);
}
var result = Build();
return result;
}
public override ContentData Build()
{
var now = _now ?? DateTime.Now;
var versionId = _versionId ?? 1;
var writerId = _writerId ?? -1;
var templateId = _templateId ?? 0;
var published = _published ?? true;
var properties = _properties ?? new Dictionary<string, PropertyData[]>();
var cultureInfos = _cultureInfos ?? new Dictionary<string, CultureVariation>();
var segment = _segment ?? _name.ToLower().ReplaceNonAlphanumericChars('-');
var contentData = new ContentData(
_name,
segment,
versionId,
now,
writerId,
templateId,
published,
properties,
cultureInfos);
return contentData;
}
public static ContentData CreateBasic(string name, DateTime? versionDate = null)
=> new ContentDataBuilder()
.WithName(name)
.WithVersionDate(versionDate ?? DateTime.Now)
.Build();
public static ContentData CreateVariant(string name, Dictionary<string, CultureVariation> cultureInfos, DateTime? versionDate = null, bool published = true)
=> new ContentDataBuilder()
.WithName(name)
.WithVersionDate(versionDate ?? DateTime.Now)
.WithCultureInfos(cultureInfos)
.WithPublished(published)
.Build();
}