Skip to content

Instantly share code, notes, and snippets.

@ReubenBond
Created January 9, 2019 21:50
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ReubenBond/cdfc1d8c4a5e87458586a39cb5554b92 to your computer and use it in GitHub Desktop.
Save ReubenBond/cdfc1d8c4a5e87458586a39cb5554b92 to your computer and use it in GitHub Desktop.
using System;
using System.Linq;
using Microsoft.Extensions.DependencyInjection;
using Newtonsoft.Json;
using Orleans;
using Orleans.Runtime;
using Orleans.Serialization;
namespace Tester
{
[AttributeUsage(AttributeTargets.Assembly)]
public sealed class UseJsonSerializerAttribute : Attribute
{
}
public sealed class OptInJsonSerializer : IExternalSerializer
{
private readonly Lazy<JsonSerializerSettings> settings;
public OptInJsonSerializer(IServiceProvider services)
{
this.settings = new Lazy<JsonSerializerSettings>(() =>
{
var typeResolver = services.GetRequiredService<ITypeResolver>();
var grainFactory = services.GetRequiredService<IGrainFactory>();
var result = OrleansJsonSerializer.GetDefaultSerializerSettings(typeResolver, grainFactory);
// Modify JSON settings as needed.
return result;
});
}
public bool IsSupportedType(Type itemType) =>
itemType.Assembly.GetCustomAttributes(typeof(UseJsonSerializerAttribute), false).Any();
/// <inheritdoc />
public object DeepCopy(object source, ICopyContext context)
{
if (source == null)
{
return null;
}
var serializationContext = new SerializationContext(context.GetSerializationManager())
{
StreamWriter = new BinaryTokenStreamWriter()
};
this.Serialize(source, serializationContext, source.GetType());
var deserializationContext = new DeserializationContext(context.GetSerializationManager())
{
StreamReader = new BinaryTokenStreamReader(serializationContext.StreamWriter.ToBytes())
};
var retVal = this.Deserialize(source.GetType(), deserializationContext);
serializationContext.StreamWriter.ReleaseBuffers();
return retVal;
}
/// <inheritdoc />
public object Deserialize(Type expectedType, IDeserializationContext context)
{
if (context == null)
{
throw new ArgumentNullException(nameof(context));
}
var reader = context.StreamReader;
var marker = reader.ReadByte();
if (marker != 0)
{
var message = $"{nameof(Orleans.Serialization.ThunderheadJsonSerializer)}.{nameof(this.Deserialize)} encountered header with value 0x{marker:X2} but this value is not supported.";
throw new NotSupportedException(message);
}
var str = reader.ReadString();
return JsonConvert.DeserializeObject(str, expectedType, this.settings.Value);
}
/// <inheritdoc />
public void Serialize(object item, ISerializationContext context, Type expectedType)
{
if (context == null)
{
throw new ArgumentNullException(nameof(context));
}
var writer = context.StreamWriter;
var str = JsonConvert.SerializeObject(item, expectedType, this.settings.Value);
writer.Write((byte)0);
writer.Write(str);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment