Cleans up some code, adds code comments
This commit is contained in:
@@ -3,18 +3,21 @@ using CSharpTest.Net.Serialization;
|
||||
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
class ContentDataSerializer : ISerializer<ContentData>
|
||||
/// <summary>
|
||||
/// Serializes/Deserializes data to BTree data source for <see cref="ContentData"/>
|
||||
/// </summary>
|
||||
internal class ContentDataSerializer : ISerializer<ContentData>
|
||||
{
|
||||
public ContentDataSerializer(IDictionaryOfPropertyDataSerializer dictionaryOfPropertyDataSerializer = null)
|
||||
{
|
||||
_dictionaryOfPropertyDataSerializer = dictionaryOfPropertyDataSerializer;
|
||||
if(_dictionaryOfPropertyDataSerializer == null)
|
||||
{
|
||||
_dictionaryOfPropertyDataSerializer = PropertiesSerializer;
|
||||
_dictionaryOfPropertyDataSerializer = DefaultPropertiesSerializer;
|
||||
}
|
||||
}
|
||||
private static readonly DictionaryOfPropertyDataSerializer PropertiesSerializer = new DictionaryOfPropertyDataSerializer();
|
||||
private static readonly DictionaryOfCultureVariationSerializer CultureVariationsSerializer = new DictionaryOfCultureVariationSerializer();
|
||||
private static readonly DictionaryOfPropertyDataSerializer DefaultPropertiesSerializer = new DictionaryOfPropertyDataSerializer();
|
||||
private static readonly DictionaryOfCultureVariationSerializer DefaultCultureVariationsSerializer = new DictionaryOfCultureVariationSerializer();
|
||||
private readonly IDictionaryOfPropertyDataSerializer _dictionaryOfPropertyDataSerializer;
|
||||
|
||||
public ContentData ReadFrom(Stream stream)
|
||||
@@ -29,7 +32,7 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
WriterId = PrimitiveSerializer.Int32.ReadFrom(stream),
|
||||
TemplateId = PrimitiveSerializer.Int32.ReadFrom(stream),
|
||||
Properties = _dictionaryOfPropertyDataSerializer.ReadFrom(stream), // TODO: We don't want to allocate empty arrays
|
||||
CultureInfos = CultureVariationsSerializer.ReadFrom(stream) // TODO: We don't want to allocate empty arrays
|
||||
CultureInfos = DefaultCultureVariationsSerializer.ReadFrom(stream) // TODO: We don't want to allocate empty arrays
|
||||
};
|
||||
}
|
||||
|
||||
@@ -46,7 +49,7 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
PrimitiveSerializer.Int32.WriteTo(value.TemplateId.Value, stream);
|
||||
}
|
||||
_dictionaryOfPropertyDataSerializer.WriteTo(value.Properties, stream);
|
||||
CultureVariationsSerializer.WriteTo(value.CultureInfos, stream);
|
||||
DefaultCultureVariationsSerializer.WriteTo(value.CultureInfos, stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,6 +6,9 @@ using Umbraco.Core;
|
||||
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
/// <summary>
|
||||
/// Serializes/Deserializes culture variant data as a dictionary for BTree
|
||||
/// </summary>
|
||||
internal class DictionaryOfCultureVariationSerializer : SerializerBase, ISerializer<IReadOnlyDictionary<string, CultureVariation>>
|
||||
{
|
||||
public IReadOnlyDictionary<string, CultureVariation> ReadFrom(Stream stream)
|
||||
|
||||
@@ -6,6 +6,9 @@ using Umbraco.Core;
|
||||
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
/// <summary>
|
||||
/// Serializes/Deserializes property data as a dictionary for BTree
|
||||
/// </summary>
|
||||
internal class DictionaryOfPropertyDataSerializer : SerializerBase, ISerializer<IDictionary<string, PropertyData[]>>, IDictionaryOfPropertyDataSerializer
|
||||
{
|
||||
public IDictionary<string, PropertyData[]> ReadFrom(Stream stream)
|
||||
|
||||
@@ -3,7 +3,9 @@ using System.Collections.Generic;
|
||||
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
// represents everything that is specific to edited or published version
|
||||
/// <summary>
|
||||
/// Represents everything that is specific to an edited or published content version
|
||||
/// </summary>
|
||||
internal class ContentData
|
||||
{
|
||||
public string Name { get; set; }
|
||||
|
||||
@@ -1,19 +1,19 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
// TODO: We need a better name, not sure why the class is called ContentNested in the first place
|
||||
// TODO: We need better names if possible, not sure why the class is called ContentNested in the first place
|
||||
|
||||
/// <summary>
|
||||
/// Serializes/Deserializes <see cref="ContentNestedData"/> document to the SQL Database as bytes
|
||||
/// </summary>
|
||||
public interface IContentNestedDataByteSerializer : IContentNestedDataSerializer
|
||||
{
|
||||
ContentNestedData DeserializeBytes(byte[] data);
|
||||
byte[] SerializeBytes(ContentNestedData nestedData);
|
||||
}
|
||||
|
||||
// TODO: We need a better name, not sure why the class is called ContentNested in the first place
|
||||
/// <summary>
|
||||
/// Serializes/Deserializes <see cref="ContentNestedData"/> document to the SQL Database as a string
|
||||
/// </summary>
|
||||
public interface IContentNestedDataSerializer
|
||||
{
|
||||
ContentNestedData Deserialize(string data);
|
||||
|
||||
@@ -13,6 +13,8 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
/// </summary>
|
||||
internal class LazyCompressedString
|
||||
{
|
||||
// TODO: This could be a struct
|
||||
|
||||
private byte[] _bytes;
|
||||
private string _str;
|
||||
|
||||
|
||||
@@ -9,26 +9,10 @@ using K4os.Compression.LZ4;
|
||||
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
/// <summary>
|
||||
/// If/where to compress custom properties for nucache
|
||||
/// </summary>
|
||||
public enum NucachePropertyCompressionLevel
|
||||
{
|
||||
None = 0,
|
||||
SQLDatabase = 1,
|
||||
NuCacheDatabase = 2
|
||||
}
|
||||
/// <summary>
|
||||
/// If/where to decompress custom properties for nucache
|
||||
/// </summary>
|
||||
public enum NucachePropertyDecompressionLevel
|
||||
{
|
||||
NotCompressed = 0,
|
||||
Immediate = 1,
|
||||
Lazy = 2
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Serializes/Deserializes property data as a dictionary for BTree with Lz4 compression options
|
||||
/// </summary>
|
||||
internal class Lz4DictionaryOfPropertyDataSerializer : SerializerBase, ISerializer<IDictionary<string, PropertyData[]>>, IDictionaryOfPropertyDataSerializer
|
||||
{
|
||||
private readonly IReadOnlyDictionary<string, NuCacheCompressionOptions> _compressProperties;
|
||||
@@ -58,7 +42,7 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
|
||||
// read property alias
|
||||
var alias = PrimitiveSerializer.String.ReadFrom(stream);
|
||||
var map = GetDeSerializationMap(alias);
|
||||
var map = GetDeserializationMap(alias);
|
||||
var key = string.Intern(map.MappedAlias ?? alias);
|
||||
|
||||
// read values count
|
||||
@@ -82,23 +66,30 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
pdata.Segment = ReadStringObject(stream, true) ?? string.Empty;
|
||||
pdata.Value = ReadObject(stream);
|
||||
|
||||
if ((map.CompressLevel.Equals(NucachePropertyCompressionLevel.NuCacheDatabase) || map.CompressLevel.Equals(NucachePropertyCompressionLevel.SQLDatabase))
|
||||
&& pdata.Value != null && pdata.Value is byte[] byteArrayValue)
|
||||
{
|
||||
//Compressed string
|
||||
switch (map.DecompressLevel)
|
||||
{
|
||||
case NucachePropertyDecompressionLevel.Lazy:
|
||||
pdata.Value = new LazyCompressedString(byteArrayValue);
|
||||
break;
|
||||
case NucachePropertyDecompressionLevel.NotCompressed:
|
||||
break;//Shouldn't be any not compressed
|
||||
case NucachePropertyDecompressionLevel.Immediate:
|
||||
default:
|
||||
pdata.Value = Encoding.UTF8.GetString(LZ4Pickler.Unpickle(byteArrayValue));
|
||||
break;
|
||||
}
|
||||
}
|
||||
switch (map.CompressLevel)
|
||||
{
|
||||
case NucachePropertyCompressionLevel.SQLDatabase:
|
||||
case NucachePropertyCompressionLevel.NuCacheDatabase:
|
||||
if (!(pdata.Value is null) && pdata.Value is byte[] byteArrayValue)
|
||||
{
|
||||
//Compressed string
|
||||
switch (map.DecompressLevel)
|
||||
{
|
||||
case NucachePropertyDecompressionLevel.Lazy:
|
||||
pdata.Value = new LazyCompressedString(byteArrayValue);
|
||||
break;
|
||||
case NucachePropertyDecompressionLevel.NotCompressed:
|
||||
//Shouldn't be any not compressed
|
||||
// TODO: Do we need to throw here?
|
||||
break;
|
||||
case NucachePropertyDecompressionLevel.Immediate:
|
||||
default:
|
||||
pdata.Value = Encoding.UTF8.GetString(LZ4Pickler.Unpickle(byteArrayValue));
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
dict[key] = pdatas.ToArray();
|
||||
@@ -131,17 +122,30 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
WriteObject(pdata.Culture ?? string.Empty, stream);
|
||||
WriteObject(pdata.Segment ?? string.Empty, stream);
|
||||
|
||||
//Only compress strings
|
||||
if (pdata.Value is string stringValue && pdata.Value != null && map.CompressLevel.Equals(NucachePropertyCompressionLevel.NuCacheDatabase)
|
||||
&& (_nucachePropertyOptions.MinimumCompressibleStringLength == null
|
||||
|| !_nucachePropertyOptions.MinimumCompressibleStringLength.HasValue
|
||||
|| stringValue.Length > _nucachePropertyOptions.MinimumCompressibleStringLength.Value))
|
||||
//Only compress strings
|
||||
switch (map.CompressLevel)
|
||||
{
|
||||
var stringBytes = Encoding.UTF8.GetBytes(stringValue);
|
||||
var compressedBytes = LZ4Pickler.Pickle(stringBytes, _nucachePropertyOptions.LZ4CompressionLevel);
|
||||
WriteObject(compressedBytes, stream);
|
||||
// If we're compressing into btree at the property level
|
||||
case NucachePropertyCompressionLevel.NuCacheDatabase:
|
||||
|
||||
if (pdata.Value is string stringValue && !(pdata.Value is null)
|
||||
&& (_nucachePropertyOptions.MinimumCompressibleStringLength is null
|
||||
|| !_nucachePropertyOptions.MinimumCompressibleStringLength.HasValue
|
||||
|| stringValue.Length > _nucachePropertyOptions.MinimumCompressibleStringLength.Value))
|
||||
{
|
||||
var stringBytes = Encoding.UTF8.GetBytes(stringValue);
|
||||
var compressedBytes = LZ4Pickler.Pickle(stringBytes, _nucachePropertyOptions.LZ4CompressionLevel);
|
||||
WriteObject(compressedBytes, stream);
|
||||
}
|
||||
else
|
||||
{
|
||||
WriteObject(pdata.Value, stream);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
WriteObject(pdata.Value, stream);
|
||||
break;
|
||||
}
|
||||
WriteObject(pdata.Value, stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -150,7 +154,7 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
|
||||
public NuCacheCompressionOptions GetSerializationMap(string propertyAlias)
|
||||
{
|
||||
if (_compressProperties == null)
|
||||
if (_compressProperties is null)
|
||||
{
|
||||
return DefaultMap;
|
||||
}
|
||||
@@ -161,9 +165,9 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
|
||||
return DefaultMap;
|
||||
}
|
||||
public NuCacheCompressionOptions GetDeSerializationMap(string propertyAlias)
|
||||
public NuCacheCompressionOptions GetDeserializationMap(string propertyAlias)
|
||||
{
|
||||
if (_uncompressProperties == null)
|
||||
if (_uncompressProperties is null)
|
||||
{
|
||||
return DefaultMap;
|
||||
}
|
||||
|
||||
@@ -9,6 +9,9 @@ using System.Text;
|
||||
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
/// <summary>
|
||||
/// Serializes/Deserializes <see cref="ContentNestedData"/> document to the SQL Database as bytes using MessagePack
|
||||
/// </summary>
|
||||
internal class MsgPackContentNestedDataSerializer : IContentNestedDataByteSerializer
|
||||
{
|
||||
private MessagePackSerializerOptions _options;
|
||||
@@ -65,7 +68,7 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
/// <param name="nestedData"></param>
|
||||
private void Optimize(ContentNestedData nestedData)
|
||||
{
|
||||
if (_propertyOptions.PropertyMap != null && _propertyOptions.PropertyMap.Any())
|
||||
if (_propertyOptions.PropertyMap != null && _propertyOptions.PropertyMap.Count > 0)
|
||||
{
|
||||
foreach (var map in _propertyOptions.PropertyMap)
|
||||
{
|
||||
@@ -79,10 +82,13 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// if there is an alias map for this property then use that instead of the real property alias
|
||||
// (used to save memory, the mapped alias is normally a single char or at least a smaller string)
|
||||
if (map.Value.MappedAlias != null && !map.Key.Equals(map.Value.MappedAlias)
|
||||
&& nestedData.PropertyData.Remove(map.Key) && nestedData.PropertyData.TryGetValue(map.Key, out PropertyData[] properties2))
|
||||
&& nestedData.PropertyData.Remove(map.Key)
|
||||
&& nestedData.PropertyData.TryGetValue(map.Key, out PropertyData[] properties2))
|
||||
{
|
||||
nestedData.PropertyData.Remove(map.Key);
|
||||
nestedData.PropertyData.Add(map.Value.MappedAlias, properties2);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -14,6 +14,13 @@ namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
|
||||
public NucachePropertyCompressionLevel CompressLevel { get; private set; }
|
||||
public NucachePropertyDecompressionLevel DecompressLevel { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Used to map a real property alias to a shorter moniker in memory
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// This is simply a memory saving mechanism
|
||||
/// </remarks>
|
||||
public string MappedAlias { get; private set; }
|
||||
|
||||
public override bool Equals(object obj)
|
||||
|
||||
@@ -0,0 +1,23 @@
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
/// <summary>
|
||||
/// If/where to compress custom properties for nucache
|
||||
/// </summary>
|
||||
public enum NucachePropertyCompressionLevel
|
||||
{
|
||||
None = 0,
|
||||
|
||||
/// <summary>
|
||||
/// Compress property data at the nucache SQL DB table level
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// Only necessary if the document in the nucache SQL DB table isn't stored as compressed bytes
|
||||
/// </remarks>
|
||||
SQLDatabase = 1,
|
||||
|
||||
/// <summary>
|
||||
/// Compress property data at the nucache BTree level
|
||||
/// </summary>
|
||||
NuCacheDatabase = 2
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
namespace Umbraco.Web.PublishedCache.NuCache.DataSource
|
||||
{
|
||||
/// <summary>
|
||||
/// If/where to decompress custom properties for nucache
|
||||
/// </summary>
|
||||
public enum NucachePropertyDecompressionLevel
|
||||
{
|
||||
NotCompressed = 0,
|
||||
Immediate = 1,
|
||||
Lazy = 2
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user