DX: Add BlockValue constructors to force correct property editor alias and layout item type (#16266)
* Improve getting and initializing new block value layouts * Remove unnecessary generic type constraints * Add and use new block value/layout item constructors in tests * Removed GetLayouts that did not make sense * Added constructor to BlockItemData to simplify explicit usages --------- Co-authored-by: kjac <kja@umbraco.dk>
This commit is contained in:
@@ -8,21 +8,10 @@ namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
/// </summary>
|
||||
public class BlockEditorData<TValue, TLayout>
|
||||
where TValue : BlockValue<TLayout>, new()
|
||||
where TLayout : class, IBlockLayoutItem, new()
|
||||
where TLayout : IBlockLayoutItem
|
||||
{
|
||||
private readonly string _propertyEditorAlias;
|
||||
|
||||
public BlockEditorData(
|
||||
string propertyEditorAlias,
|
||||
IEnumerable<ContentAndSettingsReference> references,
|
||||
TValue blockValue)
|
||||
public BlockEditorData(IEnumerable<ContentAndSettingsReference> references, TValue blockValue)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(propertyEditorAlias))
|
||||
{
|
||||
throw new ArgumentException($"'{nameof(propertyEditorAlias)}' cannot be null or whitespace", nameof(propertyEditorAlias));
|
||||
}
|
||||
|
||||
_propertyEditorAlias = propertyEditorAlias;
|
||||
BlockValue = blockValue ?? throw new ArgumentNullException(nameof(blockValue));
|
||||
References = references != null
|
||||
? new List<ContentAndSettingsReference>(references)
|
||||
@@ -30,17 +19,14 @@ public class BlockEditorData<TValue, TLayout>
|
||||
}
|
||||
|
||||
private BlockEditorData()
|
||||
{
|
||||
_propertyEditorAlias = string.Empty;
|
||||
BlockValue = new TValue();
|
||||
}
|
||||
=> BlockValue = new TValue();
|
||||
|
||||
public static BlockEditorData<TValue, TLayout> Empty { get; } = new();
|
||||
|
||||
/// <summary>
|
||||
/// Returns the layout for this specific property editor
|
||||
/// </summary>
|
||||
public IEnumerable<TLayout>? Layout => BlockValue.GetLayouts(_propertyEditorAlias);
|
||||
public IEnumerable<TLayout>? Layout => BlockValue.GetLayouts();
|
||||
|
||||
/// <summary>
|
||||
/// Returns the reference to the original BlockValue
|
||||
|
||||
@@ -13,7 +13,7 @@ namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
/// </summary>
|
||||
public abstract class BlockEditorDataConverter<TValue, TLayout>
|
||||
where TValue : BlockValue<TLayout>, new()
|
||||
where TLayout : class, IBlockLayoutItem, new()
|
||||
where TLayout : IBlockLayoutItem
|
||||
{
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
@@ -42,7 +42,7 @@ public abstract class BlockEditorDataConverter<TValue, TLayout>
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
blockEditorData = null;
|
||||
blockEditorData = default;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -62,15 +62,13 @@ public abstract class BlockEditorDataConverter<TValue, TLayout>
|
||||
|
||||
public BlockEditorData<TValue, TLayout> Convert(TValue? value)
|
||||
{
|
||||
var propertyEditorAlias = new TValue().PropertyEditorAlias;
|
||||
IEnumerable<TLayout>? layouts = value?.GetLayouts(propertyEditorAlias);
|
||||
if (layouts is null)
|
||||
if (value?.GetLayouts() is not IEnumerable<TLayout> layouts)
|
||||
{
|
||||
return BlockEditorData<TValue, TLayout>.Empty;
|
||||
}
|
||||
|
||||
IEnumerable<ContentAndSettingsReference> references = GetBlockReferences(layouts);
|
||||
|
||||
return new BlockEditorData<TValue, TLayout>(propertyEditorAlias, references, value!);
|
||||
return new BlockEditorData<TValue, TLayout>(references, value);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,8 +1,14 @@
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
|
||||
public class BlockGridLayoutAreaItem
|
||||
{
|
||||
public Guid Key { get; set; } = Guid.Empty;
|
||||
|
||||
public BlockGridLayoutItem[] Items { get; set; } = Array.Empty<BlockGridLayoutItem>();
|
||||
|
||||
public BlockGridLayoutAreaItem()
|
||||
{ }
|
||||
|
||||
public BlockGridLayoutAreaItem(Guid key)
|
||||
=> Key = key;
|
||||
}
|
||||
|
||||
@@ -17,4 +17,14 @@ public class BlockGridLayoutItem : IBlockLayoutItem
|
||||
public int? RowSpan { get; set; }
|
||||
|
||||
public BlockGridLayoutAreaItem[] Areas { get; set; } = Array.Empty<BlockGridLayoutAreaItem>();
|
||||
|
||||
public BlockGridLayoutItem()
|
||||
{ }
|
||||
|
||||
public BlockGridLayoutItem(Udi contentUdi)
|
||||
=> ContentUdi = contentUdi;
|
||||
|
||||
public BlockGridLayoutItem(Udi contentUdi, Udi settingsUdi)
|
||||
: this(contentUdi)
|
||||
=> SettingsUdi = settingsUdi;
|
||||
}
|
||||
|
||||
@@ -1,6 +1,23 @@
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
|
||||
/// <summary>
|
||||
/// Represents a block grid value.
|
||||
/// </summary>
|
||||
public class BlockGridValue : BlockValue<BlockGridLayoutItem>
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="BlockGridValue" /> class.
|
||||
/// </summary>
|
||||
public BlockGridValue()
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="BlockGridValue" /> class.
|
||||
/// </summary>
|
||||
/// <param name="layouts">The layouts.</param>
|
||||
public BlockGridValue(IEnumerable<BlockGridLayoutItem> layouts)
|
||||
=> Layout[PropertyEditorAlias] = layouts;
|
||||
|
||||
/// <inheritdoc />
|
||||
public override string PropertyEditorAlias => Constants.PropertyEditors.Aliases.BlockGrid;
|
||||
}
|
||||
|
||||
@@ -10,6 +10,17 @@ namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
/// </summary>
|
||||
public class BlockItemData
|
||||
{
|
||||
public BlockItemData()
|
||||
{
|
||||
}
|
||||
|
||||
public BlockItemData(Udi udi, Guid contentTypeKey, string contentTypeAlias)
|
||||
{
|
||||
ContentTypeAlias = contentTypeAlias;
|
||||
Udi = udi;
|
||||
ContentTypeKey = contentTypeKey;
|
||||
}
|
||||
|
||||
public Guid ContentTypeKey { get; set; }
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -11,4 +11,14 @@ public class BlockListLayoutItem : IBlockLayoutItem
|
||||
public Udi? ContentUdi { get; set; }
|
||||
|
||||
public Udi? SettingsUdi { get; set; }
|
||||
|
||||
public BlockListLayoutItem()
|
||||
{ }
|
||||
|
||||
public BlockListLayoutItem(Udi contentUdi)
|
||||
=> ContentUdi = contentUdi;
|
||||
|
||||
public BlockListLayoutItem(Udi contentUdi, Udi settingsUdi)
|
||||
: this(contentUdi)
|
||||
=> SettingsUdi = settingsUdi;
|
||||
}
|
||||
|
||||
@@ -1,6 +1,23 @@
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
|
||||
/// <summary>
|
||||
/// Represents a block list value.
|
||||
/// </summary>
|
||||
public class BlockListValue : BlockValue<BlockListLayoutItem>
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="BlockListValue" /> class.
|
||||
/// </summary>
|
||||
public BlockListValue()
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="BlockListValue" /> class.
|
||||
/// </summary>
|
||||
/// <param name="layouts">The layouts.</param>
|
||||
public BlockListValue(IEnumerable<BlockListLayoutItem> layouts)
|
||||
=> Layout[PropertyEditorAlias] = layouts;
|
||||
|
||||
/// <inheritdoc />
|
||||
public override string PropertyEditorAlias => Constants.PropertyEditors.Aliases.BlockList;
|
||||
}
|
||||
|
||||
@@ -3,22 +3,56 @@
|
||||
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
|
||||
/// <summary>
|
||||
/// Represents a block value.
|
||||
/// </summary>
|
||||
public abstract class BlockValue
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the layout for specific property editors.
|
||||
/// </summary>
|
||||
/// <value>
|
||||
/// The layout.
|
||||
/// </value>
|
||||
public IDictionary<string, IEnumerable<IBlockLayoutItem>> Layout { get; set; } = new Dictionary<string, IEnumerable<IBlockLayoutItem>>();
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the content data.
|
||||
/// </summary>
|
||||
/// <value>
|
||||
/// The content data.
|
||||
/// </value>
|
||||
public List<BlockItemData> ContentData { get; set; } = [];
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the settings data.
|
||||
/// </summary>
|
||||
/// <value>
|
||||
/// The settings data.
|
||||
/// </value>
|
||||
public List<BlockItemData> SettingsData { get; set; } = [];
|
||||
|
||||
/// <summary>
|
||||
/// Gets the property editor alias of the current layout.
|
||||
/// </summary>
|
||||
/// <value>
|
||||
/// The property editor alias of the current layout.
|
||||
/// </value>
|
||||
public abstract string PropertyEditorAlias { get; }
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public abstract class BlockValue<TLayout> : BlockValue
|
||||
where TLayout : IBlockLayoutItem
|
||||
{
|
||||
public IEnumerable<TLayout>? GetLayouts(string propertyEditorAlias)
|
||||
=> Layout.TryGetValue(propertyEditorAlias, out IEnumerable<IBlockLayoutItem>? layouts) is true
|
||||
/// <summary>
|
||||
/// Gets the layouts of the current property editor.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// The layouts.
|
||||
/// </returns>
|
||||
public IEnumerable<TLayout>? GetLayouts()
|
||||
=> Layout.TryGetValue(PropertyEditorAlias, out IEnumerable<IBlockLayoutItem>? layouts)
|
||||
? layouts.OfType<TLayout>()
|
||||
: null;
|
||||
}
|
||||
|
||||
public abstract class BlockValue
|
||||
{
|
||||
public IDictionary<string, IEnumerable<IBlockLayoutItem>> Layout { get; set; } = new Dictionary<string, IEnumerable<IBlockLayoutItem>>();
|
||||
|
||||
public List<BlockItemData> ContentData { get; set; } = new();
|
||||
|
||||
public List<BlockItemData> SettingsData { get; set; } = new();
|
||||
|
||||
public abstract string PropertyEditorAlias { get; }
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright (c) Umbraco.
|
||||
// Copyright (c) Umbraco.
|
||||
// See LICENSE for more details.
|
||||
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
@@ -11,4 +11,14 @@ public class RichTextBlockLayoutItem : IBlockLayoutItem
|
||||
public Udi? ContentUdi { get; set; }
|
||||
|
||||
public Udi? SettingsUdi { get; set; }
|
||||
|
||||
public RichTextBlockLayoutItem()
|
||||
{ }
|
||||
|
||||
public RichTextBlockLayoutItem(Udi contentUdi)
|
||||
=> ContentUdi = contentUdi;
|
||||
|
||||
public RichTextBlockLayoutItem(Udi contentUdi, Udi settingsUdi)
|
||||
: this(contentUdi)
|
||||
=> SettingsUdi = settingsUdi;
|
||||
}
|
||||
|
||||
@@ -1,6 +1,23 @@
|
||||
namespace Umbraco.Cms.Core.Models.Blocks;
|
||||
|
||||
/// <summary>
|
||||
/// Represents a rich text block value.
|
||||
/// </summary>
|
||||
public class RichTextBlockValue : BlockValue<RichTextBlockLayoutItem>
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="RichTextBlockValue" /> class.
|
||||
/// </summary>
|
||||
public RichTextBlockValue()
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="RichTextBlockValue" /> class.
|
||||
/// </summary>
|
||||
/// <param name="layouts">The layouts.</param>
|
||||
public RichTextBlockValue(IEnumerable<RichTextBlockLayoutItem> layouts)
|
||||
=> Layout[PropertyEditorAlias] = layouts;
|
||||
|
||||
/// <inheritdoc />
|
||||
public override string PropertyEditorAlias => Constants.PropertyEditors.Aliases.TinyMce;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user