Not
Bu sayfaya erişim yetkilendirme gerektiriyor. Oturum açmayı veya dizinleri değiştirmeyi deneyebilirsiniz.
Bu sayfaya erişim yetkilendirme gerektiriyor. Dizinleri değiştirmeyi deneyebilirsiniz.
Genel olarak, Orleans içinde kullanılan iki tür serileştirme vardır.
- Taneli çağrı serileştirme: Taneciklere ve tanelerden geçirilen nesneleri seri hale getirmek için kullanılır.
- Taneli depolama serileştirme: Depolama sistemlerine ve depolama sistemlerinden nesneleri seri hale getirmek için kullanılır.
Bu makalenin çoğu, Orleans içinde yer alan serileştirme çerçevesi aracılığıyla grain call serileştirmesine odaklanır. Grain storage serializers bölümünde, taneli depolama serileştirmesi ele alınmaktadır.
Serileştirmeyi kullan Orleans
Orleansolarak adlandırılan gelişmiş ve genişletilebilir bir serileştirme çerçevesi içerir.Orleans Serileştirme. içinde yer alan Orleans serileştirme çerçevesi aşağıdaki hedefleri karşılayacak şekilde tasarlanmıştır:
- Yüksek performanslı: Seri hale getirici, performans için tasarlanmıştır ve iyileştirilmiştir. Bu sunuda daha fazla ayrıntı sağlanır.
- Yüksek aslına uygunluk: Seri hale getirici, genel türler, polimorfizm, devralma hiyerarşileri, nesne kimliği ve döngüsel grafikler desteği de dahil olmak üzere, .NET tür sisteminin çoğunu sadakatle temsil eder. İşlemler arasında taşınabilir olmadığından işaretçiler desteklenmez.
- Esneklik: Yedekler oluşturarak veya System.Text.Json, Newtonsoft.Json, MessagePack ve Google.Protobuf gibi dış serileştirme kitaplıklarına temsilci ekleyerek seri hale getiriciyi üçüncü taraf kitaplıklarını destekleyecek şekilde özelleştirebilirsiniz.
-
Sürüme dayanıklılık: Seri hale getirici, uygulama türlerinin zaman içinde gelişmesine olanak sağlayarak şunları destekler:
- Üye ekleme ve kaldırma
- Alt Sınıflama
- Sayısal genişletme ve daraltma (örn.
intto/fromlong,floatto/fromdouble) - Türleri yeniden adlandırma
Türlerin yüksek doğrulukta temsili dizgeleştiriciler için oldukça nadirdir, bu nedenle bazı noktalarda daha fazla açıklama yapmak gerekebilir.
Dinamik türler ve rastgele polimorfizm: Orleans grain çağrılarında geçirilen türlerde kısıtlamaları uygulamaz ve gerçek veri türünün dinamik doğasını korur. Bu, şu anlama gelir ki, örneğin bir taneli arabirimdeki bir yöntem IDictionary kabul etmesi gereken bir şekilde bildirilirse, ancak çalışma anında gönderen SortedDictionary<TKey,TValue> gönderirse, alıcı gerçekten bir
SortedDictionaryalır (her ne kadar "statik sözleşme"/taneli arabirim bu davranışı belirtmese bile).Nesne kimliğini koruma: Aynı nesne bir taneli çağrının bağımsız değişkenlerinde birden çok kez geçirilirse veya bağımsız değişkenlerden dolaylı olarak birden çok kez işaret edilirse, Orleans bunu yalnızca bir kez serileştirir. Alıcı tarafında, Orleans tüm referansları doğru şekilde geri yükler, böylece seri durumdan çıkarma işleminden sonra aynı nesneye yönelik iki işaretçi hala aynı nesneye işaret eder. Nesne kimliğinin korunması aşağıdaki gibi senaryolarda önemlidir: A diliminin B dilimine 100 giriş içeren bir sözlük gönderdiğini ve sözlükteki 10 anahtarın A tarafında aynı nesneye
objişaret ettiği düşünün. Nesne kimliğini korumadan B, bu 10 anahtarın 10 farklı kopyasına işaret ettiği 100 giriş içerenobjbir sözlük alır. Nesne kimliği korunduğu için, B tarafındaki sözlük A tarafında olduğu gibi görünür ve bu 10 anahtar tek bir nesneyeobjişaret ediyor. .NET'teki varsayılan dize karma kodu uygulamaları işlem başına rastgele olduğundan, sözlüklerdeki ve karma kümelerdeki değerlerin (örneğin) sıralanması korunmayabilir.
Sürüm toleransını desteklemek için serileştirici, hangi türlerin ve üyelerin serileştirildiğini belirtmeniz gerekir. Bunu mümkün olduğunca acısız hale getirmeye çalıştık. Tüm seri hale getirilebilir türleri Orleans.GenerateSerializerAttribute ile işaretleyerek türünüz için Orleans'in seri hale getirici kodu oluşturması talimatını verin. Bunu yaptıktan sonra, burada gösterildiği gibi, türlerinizdeki serileştirilebilir üyelere gerekenleri Orleans.IdAttribute eklemek için dahil edilen kod düzeltmesini kullanabilirsiniz:
Orleans içindeki serileştirilebilir bir türün, özniteliklerin nasıl uygulanacağını gösteren bir örneği burada verilmiştir.
[GenerateSerializer]
public class Employee
{
[Id(0)]
public string Name { get; set; }
}
Orleans devralmayı destekler ve hiyerarşideki tek tek katmanları ayrı ayrı seri hale getirerek ayrı üye kimliklerine sahip olmalarını sağlar.
[GenerateSerializer]
public class Publication
{
[Id(0)]
public string Title { get; set; }
}
[GenerateSerializer]
public class Book : Publication
{
[Id(0)]
public string ISBN { get; set; }
}
Önceki kodda, Publication ve Book'nin üyeleri [Id(0)] olduğunu, BookPublication'den türetilmiş olsa bile, fark edin. Tanımlayıcılar bir bütün olarak türe değil, devralma düzeyine göre belirlendiğinden, bu, Orleans içinde önerilen uygulamadır. Üyeleri PublicationBook bağımsız olarak ekleyip kaldırabilirsiniz, ancak uygulama özel dikkate alınmadan dağıtıldıktan sonra hiyerarşiye yeni bir temel sınıf ekleyemezsiniz.
Orleans, internal, ve private üyelerine sahip türleri serileştirmeyi de destekler. Örneğin, bu örnek tür:
[GenerateSerializer]
public struct MyCustomStruct
{
public MyCustomStruct(int intProperty, int intField)
{
IntProperty = intProperty;
_intField = intField;
}
[Id(0)]
public int IntProperty { get; }
[Id(1)] private readonly int _intField;
public int GetIntField() => _intField;
public override string ToString() => $"{nameof(_intField)}: {_intField}, {nameof(IntProperty)}: {IntProperty}";
}
Varsayılan olarak, Orleans tam adını kodlayarak türünüzü serileştirir.
Orleans.AliasAttribute ekleyerek bunu geçersiz kılabilirsiniz. Temel sınıfın adının değiştirilmesine veya derlemeler arasında taşınmasına karşı dayanıklı olan bir ad kullanılarak türünüzün serileştirilmesiyle sonuçlanır. Tip takma adları küresel kapsamlıdır ve bir uygulamada aynı değere sahip iki takma ada sahip olamazsınız. Genel türler için diğer ad değeri, ters tırnak işaretiyle belirlenen genel parametrelerin sayısını içermelidir; örneğin, MyGenericType<T, U> diğer adına [Alias("mytype`2")] sahip olabilir.
record türlerini serileştirme
Kaydın birincil oluşturucusunda tanımlanan bir üye, varsayılan olarak örtük bir kimliğe sahiptir. Başka bir deyişle, Orleans türleri serileştirmeyi record destekler. Bu, uygulamanızın önceki sürümleriyle (sıralı yükseltme senaryosunda) ve depolama ve akışlarda söz konusu türün serileştirilmiş örnekleriyle uyumluluğu bozan, zaten dağıtılmış bir türün parametre sırasını değiştiremeyeceğiniz anlamına gelir. Kayıt türünün gövdesinde tanımlanan üyeler kimlikleri birincil oluşturucu parametreleriyle paylaşmaz.
[GenerateSerializer]
public record MyRecord(string A, string B)
{
// ID 0 won't clash with A in primary constructor as they don't share identities
[Id(0)]
public string C { get; init; }
}
Birincil oluşturucu parametrelerinin otomatik olarak serileştirilebilir alanlar olarak eklenmesini istemiyorsanız kullanın [GenerateSerializer(IncludePrimaryConstructorParameters = false)].
MessagePack serileştirme
Orleans 8.2'den itibaren, Orleans için MessagePack'i dış bir serileştirici olarak kullanabilirsiniz. MessagePack, hızlı serileştirme ve seri durumdan çıkarma hızlarını korurken JSON'dan daha küçük yükler üreten yüksek performanslı bir ikili serileştirme biçimidir.
MessagePack ne zaman kullanılır?
Aşağıdaki durumlarda MessagePack kullanmayı göz önünde bulundurun:
- MessagePack'i destekleyen non-.NET sistemlerle birlikte çalışabilirliğe ihtiyacınız var
- MessagePack öznitelikleri (
[MessagePackObject],[Key]) ile önceden açıklanmış türleriniz var - JSON tabanlı seri hale getiricilere kıyasla daha küçük yük boyutları istiyorsunuz
- Standartlaştırılmış bir ikili biçime ihtiyacınız var
Çoğu Orleans uygulama için, daha yüksek aslına uygunluk (.NET türü sistem desteği), nesne kimliği koruması ve otomatik seri hale getirici oluşturma sağladığından varsayılan Orleans seri hale getirici önerilir.
MessagePack seri hale getirici paketini yükleme
MessagePack seri hale getirici paketini projenize ekleyin:
dotnet add package Microsoft.Orleans.Serialization.MessagePack
MessagePack serileştirmeyi yapılandırma
MessagePack serileştirmesini yapılandırmak için uzantı yöntemini kullanın AddMessagePackSerializer :
public static void ConfigureMessagePackBasic(string[] args)
{
var builder = Host.CreateApplicationBuilder(args);
builder.UseOrleans(siloBuilder =>
{
siloBuilder.UseLocalhostClustering();
siloBuilder.Services.AddSerializer(serializerBuilder => serializerBuilder.AddMessagePackSerializer(
isSerializable: type => type.Namespace?.StartsWith("MyApp.Messages") == true,
isCopyable: type => false,
messagePackSerializerOptions: null
));
});
}
Temsilci, isSerializable MessagePack seri hale getiricisi tarafından hangi türlerin işleneceğini denetler. Bu koşulla eşleşmeyen türler varsayılan Orleans seri hale getiriciye geri döner.
MessagePackCodecOptions
MessagePack serileştiricisini MessagePackCodecOptions kullanarak yapılandırabilirsiniz.
| Mülkiyet | Türü | Varsayılan | Description |
|---|---|---|---|
SerializerOptions |
MessagePackSerializerOptions |
MessagePackSerializerOptions.Standard |
Serileştirme için kullanılacak MessagePack seri hale getirici seçenekleri. |
AllowDataContractAttributes |
bool |
false |
true olduğunda, [DataContract] ile işaretlenmiş türlerin MessagePack kullanılarak serileştirilmesine izin verir. |
IsSerializableType |
Func<Type, bool?> |
null |
Bir türün MessagePack tarafından seri hale getirilip getirilmemesi gerektiğini belirlemek için bir temsilci. |
IsCopyableType |
Func<Type, bool?> |
null |
Bir türün MessagePack tarafından kopyalanması gerekip gerekmediğini belirlemek için bir temsilci. |
Örnek: Seçeneklerle yapılandırma
public static void ConfigureMessagePackWithOptions(string[] args)
{
var builder = Host.CreateApplicationBuilder(args);
builder.UseOrleans(siloBuilder =>
{
siloBuilder.UseLocalhostClustering();
siloBuilder.Services.AddSerializer(serializerBuilder => serializerBuilder.AddMessagePackSerializer(
isSerializable: type => type.GetCustomAttribute<MessagePackObjectAttribute>() != null,
isCopyable: type => false,
configureOptions: options => options.Configure(opts =>
{
opts.SerializerOptions = MessagePackSerializerOptions.Standard
.WithCompression(MessagePackCompression.Lz4BlockArray);
opts.AllowDataContractAttributes = true;
})
));
});
}
MessagePack türlerini tanımlama
MessagePack tarafından seri hale getirilmiş türler MessagePack özniteliklerini kullanmalıdır:
[MessagePackObject]
public class OrderMessage
{
[Key(0)]
public string OrderId { get; set; }
[Key(1)]
public decimal Amount { get; set; }
[Key(2)]
public DateTime CreatedAt { get; set; }
[Key(3)]
public List<string> Items { get; set; }
}
Daha sonra bu türleri tane arabirimlerinde kullanabilirsiniz:
public interface IOrderGrain : IGrainWithStringKey
{
Task<OrderMessage> GetOrder();
Task PlaceOrder(OrderMessage order);
}
Serileştirici karşılaştırması
| Özellik | Orleans Yerel | MessagePack | System.Text.Json |
|---|---|---|---|
| Biçim | Binary | Binary | Metin (JSON) |
| .NET türü tutarlılığı | Mükemmel | İyi | Sınırlı |
| Nesne kimliği | Yes | Hayı | Hayı |
| Yük boyutu | Küçük | En Küçük | En büyük |
| Platformlar arası | Yalnızca .NET | Herhangi bir MessagePack istemcisi | Herhangi bir JSON istemcisi |
| Sürüm toleransı | Yes | Yes | Yes |
| Kurulum gerekli | Hiç kimse | Açık öznitelikler | Açık öznitelikler |
Yabancı türleri seri hale getirme vekilleri
Bazen, üzerinde tam denetime sahip olmadığınız tanecikler arasında türleri geçirmeniz gerekebilir. Böyle durumlarda, uygulama kodunuzda özel tanımlı bir türe manuel dönüştürme pratik olmayabilir. Orleans bu durumlar için bir çözüm sunar: vekil türler. Vekiller, hedef türleri yerine serileştirilir ve hedef türe ve hedef türe dönüştürme işlevlerine sahiptir. Aşağıdaki yabancı tür ve karşılık gelen vekil ve dönüştürücü örneğini göz önünde bulundurun:
// This is the foreign type, which you do not have control over.
public struct MyForeignLibraryValueType
{
public MyForeignLibraryValueType(int num, string str, DateTimeOffset dto)
{
Num = num;
String = str;
DateTimeOffset = dto;
}
public int Num { get; }
public string String { get; }
public DateTimeOffset DateTimeOffset { get; }
}
// This is the surrogate which will act as a stand-in for the foreign type.
// Surrogates should use plain fields instead of properties for better performance.
[GenerateSerializer]
public struct MyForeignLibraryValueTypeSurrogate
{
[Id(0)]
public int Num;
[Id(1)]
public string String;
[Id(2)]
public DateTimeOffset DateTimeOffset;
}
// This is a converter that converts between the surrogate and the foreign type.
[RegisterConverter]
public sealed class MyForeignLibraryValueTypeSurrogateConverter :
IConverter<MyForeignLibraryValueType, MyForeignLibraryValueTypeSurrogate>
{
public MyForeignLibraryValueType ConvertFromSurrogate(
in MyForeignLibraryValueTypeSurrogate surrogate) =>
new(surrogate.Num, surrogate.String, surrogate.DateTimeOffset);
public MyForeignLibraryValueTypeSurrogate ConvertToSurrogate(
in MyForeignLibraryValueType value) =>
new()
{
Num = value.Num,
String = value.String,
DateTimeOffset = value.DateTimeOffset
};
}
Önceki kodda:
-
MyForeignLibraryValueType, denetiminizin dışında, tüketen bir kitaplıkta tanımlanan bir türdür. -
MyForeignLibraryValueTypeSurrogateveMyForeignLibraryValueTypearasında eşleme yapan bir yedek türdür. -
RegisterConverterAttribute,
MyForeignLibraryValueTypeSurrogateConverter'in iki türü eşlemek için dönüştürücü olarak işlediğini belirtir. sınıfı arabirimini IConverter<TValue,TSurrogate> uygular.
Orleans tür hiyerarşilerindeki türlerin serileştirilmesini destekler (diğer türlerden türetilen türler). Yabancı tür bir tip hiyerarşisinde görünebilirse (örneğin, kendi türlerinizden birinin temel sınıfı olarak), arabirimi ek olarak Orleans.IPopulator<TValue,TSurrogate> uygulamanız gerekir. Aşağıdaki örneği inceleyin:
// The foreign type is not sealed, allowing other types to inherit from it.
public class MyForeignLibraryType
{
public MyForeignLibraryType() { }
public MyForeignLibraryType(int num, string str, DateTimeOffset dto)
{
Num = num;
String = str;
DateTimeOffset = dto;
}
public int Num { get; set; }
public string String { get; set; }
public DateTimeOffset DateTimeOffset { get; set; }
}
// The surrogate is defined as it was in the previous example.
[GenerateSerializer]
public struct MyForeignLibraryTypeSurrogate
{
[Id(0)]
public int Num;
[Id(1)]
public string String;
[Id(2)]
public DateTimeOffset DateTimeOffset;
}
// Implement the IConverter and IPopulator interfaces on the converter.
[RegisterConverter]
public sealed class MyForeignLibraryTypeSurrogateConverter :
IConverter<MyForeignLibraryType, MyForeignLibraryTypeSurrogate>,
IPopulator<MyForeignLibraryType, MyForeignLibraryTypeSurrogate>
{
public MyForeignLibraryType ConvertFromSurrogate(
in MyForeignLibraryTypeSurrogate surrogate) =>
new(surrogate.Num, surrogate.String, surrogate.DateTimeOffset);
public MyForeignLibraryTypeSurrogate ConvertToSurrogate(
in MyForeignLibraryType value) =>
new()
{
Num = value.Num,
String = value.String,
DateTimeOffset = value.DateTimeOffset
};
public void Populate(
in MyForeignLibraryTypeSurrogate surrogate, MyForeignLibraryType value)
{
value.Num = surrogate.Num;
value.String = surrogate.String;
value.DateTimeOffset = surrogate.DateTimeOffset;
}
}
// Application types can inherit from the foreign type, assuming they're not sealed
// since Orleans knows how to serialize it.
[GenerateSerializer]
public sealed class DerivedFromMyForeignLibraryType : MyForeignLibraryType
{
public DerivedFromMyForeignLibraryType() { }
public DerivedFromMyForeignLibraryType(
int intValue, int num, string str, DateTimeOffset dto) : base(num, str, dto)
{
IntValue = intValue;
}
[Id(0)]
public int IntValue { get; set; }
}
Sürüm oluşturma kuralları
Türleri değiştirirken bir dizi kuralı izlemeniz koşuluyla sürüm toleransı desteklenir. Google Protokol Arabellekleri (Protobuf) gibi sistemleri biliyorsanız, bu kurallar tanıdık olacaktır.
Bileşik türler (class & struct)
- Devralma desteklenir, ancak bir nesnenin devralma hiyerarşisinde değişiklik yapmak desteklenmez. Bir sınıfın temel sınıfını ekleyemez, değiştiremez veya kaldıramazsınız.
- Aşağıdaki Sayısallar bölümünde açıklanan bazı sayısal türler dışında, alan türlerini değiştiremezsiniz.
- Devralma hiyerarşisinde herhangi bir noktada alan ekleyebilir veya kaldırabilirsiniz.
- Alan kimliklerini değiştiremezsiniz.
- Alan kimlikleri bir tür hiyerarşisindeki her düzey için benzersiz olmalıdır, ancak temel sınıflar ve alt sınıflar arasında yeniden kullanılabilir. Örneğin, bir
Basesınıf kimliğine0sahip bir alan bildirebilir ve birSub : Basesınıf da aynı kimliğe0sahip farklı bir alan bildirebilir.
Sayısal veriler
- Sayısal alanın imzalılığını değiştiremezsiniz.
- arasındaki
intuintdönüştürmeler geçersiz.
- arasındaki
- Sayısal alanın genişliğini değiştirebilirsiniz.
- Örneğin,
int'denlong'e veyaulong'denushort'e dönüştürmeler desteklenir. - Alanın çalışma zamanı değeri taşma neden olursa, genişliği daraltan dönüştürmeler bir özel durum oluşturur.
-
ulong'danushort'e dönüştürme yalnızca çalışma zamanı değeriushort.MaxValue'den küçükse desteklenir. -
double'denfloat'e dönüştürmeler, yalnızca çalışma zamanı değerifloat.MinValueilefloat.MaxValuearasında olduğunda desteklenir. - Benzer şekilde,
decimal, hemdoublehem defloatile karşılaştırıldığında daha dar bir aralığa sahiptir.
- Örneğin,
Fotokopi
Orleans bazı eşzamanlılık hatası sınıflarına karşı korumayı da içeren güvenliği varsayılan olarak sağlar. Özellikle, Orleans varsayılan olarak grain çağrılarında geçirilen nesneleri hemen kopyalar. Orleans. Serileştirme bu kopyalamayı kolaylaştırır. Bir türe uyguladığınızda Orleans.CodeGeneration.GenerateSerializerAttribute , Orleans bu tür için de kopyalayıcılar oluşturur. Orleans , ile işaretlenmiş ImmutableAttributetürleri veya tek tek üyeleri kopyalamaktan kaçınıyor. Daha fazla ayrıntı için bkz . içindeki Orleanssabit türleri seri hale getirme.
Serileştirme en iyi yöntemleri
✅ özniteliğini kullanarak türlerinize diğer adlar
[Alias("my-type")]verin. Diğer adlara sahip türler, uyumsuzluğa neden olmadan yeniden adlandırılabilir.❌ Normal bir
recorddeğeriniclassveya tam tersi olarak değiştirmeyin. Kayıtlar, normal üyelere ek olarak birincil oluşturucu üyelerine sahip olduğundan kayıtlar ve sınıflar aynı şekilde temsil değildir; bu nedenle ikisi birbirinin yerine kullanılamaz.❌ Serileştirilebilir bir tür için var olan bir tür hiyerarşisine yeni türler eklemeyin. Var olan bir türe yeni bir temel sınıf eklememelisiniz. Mevcut bir türe güvenli bir şekilde yeni bir alt sınıf ekleyebilirsiniz.
✅ kullanımlarını SerializableAttribute ve buna karşılık gelen GenerateSerializerAttribute bildirimlerle IdAttribute değiştirin.
✅Her tür için tüm üye kimliklerini sıfırdan başlatın. Bir alt sınıftaki ve temel sınıfındaki kimlikler güvenli bir şekilde çakışabilir. Aşağıdaki örnekteki her iki özelliğin de kimlikleri
0ile aynıdır.[GenerateSerializer] public class MyBaseClass { [Id(0)] public int MyBaseInt { get; set; } } [GenerateSerializer] public sealed class MySubClass : MyBaseClass { [Id(0)] public int MySubInt { get; set; } }✅ Gerektiğinde sayısal üye türlerini genişletme. olarak genişletebilirsiniz
sbyteshortintlong.- Sayısal üye türlerini daraltabilirsiniz, ancak gözlemlenen değerler daraltılmış tür tarafından doğru şekilde temsil edilemiyorsa bu, çalışma zamanı hatasıyla sonuçlanır. Örneğin,
int.MaxValuebirshortalan tarafından temsil edilemez, bu nedenle birintalanınshortdaraltılması, böyle bir değerle karşılaşılırsa çalışma zamanı özel durumuyla sonuçlanabilir.
- Sayısal üye türlerini daraltabilirsiniz, ancak gözlemlenen değerler daraltılmış tür tarafından doğru şekilde temsil edilemiyorsa bu, çalışma zamanı hatasıyla sonuçlanır. Örneğin,
❌ Sayısal tür üyesinin imzalılığını değiştirmeyin. Örneğin, bir üyenin türünü
uintintolarak veyaintuintolarak değiştirmemelisiniz.
Tahıl depolama serileştiricileri
Orleans özelliği aracılığıyla State erişilen veya tahılınıza bir veya daha fazla IPersistentState<TState> değer eklenerek tanecikler için sağlayıcı destekli kalıcılık modeli içerir. 7.0'ın öncesinde Orleans her sağlayıcının serileştirmeyi yapılandırmak için farklı bir mekanizması vardı. 7.0'da Orleans , her sağlayıcı için durum serileştirmesini özelleştirmek için tutarlı bir yol sunan genel amaçlı bir tanecik durum serileştirici arabirimi IGrainStorageSerializervardır. Desteklenen depolama sağlayıcıları, sağlayıcının IStorageProviderSerializerOptions.GrainStorageSerializer seçenekler sınıfında özelliği ayarlamayı içeren bir desen uygular, örneğin:
- DynamoDBStorageOptions.GrainStorageSerializer
- AzureBlobStorageOptions.GrainStorageSerializer
- AzureTableStorageOptions.GrainStorageSerializer
- GrainStorageSerializer
Tahıl depolama serileştirmesi şu anda durumu seri hale getirmek için varsayılan olarak Newtonsoft.Json ayarlanmıştır. Yapılandırma zamanında bu özelliği değiştirerek bunu değiştirebilirsiniz. Aşağıdaki örnekte OptionsBuilder<TOptions kullanılarak bu gösterilmektedir>:
public static void ConfigureGrainStorageSerializer(ISiloBuilder siloBuilder)
{
siloBuilder.AddAzureBlobGrainStorage(
"MyGrainStorage",
(OptionsBuilder<AzureBlobStorageOptions> optionsBuilder) =>
{
optionsBuilder.Configure<MyCustomSerializer>(
(options, serializer) => options.GrainStorageSerializer = serializer);
});
}
Daha fazla bilgi için bkz . OptionsBuilder API'si.
Genel olarak, Orleans içinde kullanılan iki tür serileştirme vardır.
- Taneli çağrı serileştirme: Taneciklere ve tanelerden geçirilen nesneleri seri hale getirmek için kullanılır.
- Taneli depolama serileştirme: Depolama sistemlerine ve depolama sistemlerinden nesneleri seri hale getirmek için kullanılır.
Bu makalenin çoğu, Orleans içinde yer alan serileştirme çerçevesi aracılığıyla grain call serileştirmesine odaklanır. Grain storage serializers bölümünde, taneli depolama serileştirmesi ele alınmaktadır.
Serileştirmeyi kullan Orleans
Orleansolarak adlandırılan gelişmiş ve genişletilebilir bir serileştirme çerçevesi içerir.Orleans Serileştirme. içinde yer alan Orleans serileştirme çerçevesi aşağıdaki hedefleri karşılayacak şekilde tasarlanmıştır:
- Yüksek performanslı: Seri hale getirici, performans için tasarlanmıştır ve iyileştirilmiştir. Bu sunuda daha fazla ayrıntı sağlanır.
- Yüksek aslına uygunluk: Seri hale getirici, genel türler, polimorfizm, devralma hiyerarşileri, nesne kimliği ve döngüsel grafikler desteği de dahil olmak üzere, .NET tür sisteminin çoğunu sadakatle temsil eder. İşlemler arasında taşınabilir olmadığından işaretçiler desteklenmez.
- Esneklik: Yedekler oluşturarak veya System.Text.Json, Newtonsoft.Json ve Google.Protobuf gibi dış serileştirme kitaplıklarına temsilci ekleyerek seri hale getiriciyi üçüncü taraf kitaplıklarını destekleyecek şekilde özelleştirebilirsiniz.
-
Sürüme dayanıklılık: Seri hale getirici, uygulama türlerinin zaman içinde gelişmesine olanak sağlayarak şunları destekler:
- Üye ekleme ve kaldırma
- Alt Sınıflama
- Sayısal genişletme ve daraltma (örn.
intto/fromlong,floatto/fromdouble) - Türleri yeniden adlandırma
Türlerin yüksek doğrulukta temsili dizgeleştiriciler için oldukça nadirdir, bu nedenle bazı noktalarda daha fazla açıklama yapmak gerekebilir.
Dinamik türler ve rastgele polimorfizm: Orleans grain çağrılarında geçirilen türlerde kısıtlamaları uygulamaz ve gerçek veri türünün dinamik doğasını korur. Bu, şu anlama gelir ki, örneğin bir taneli arabirimdeki bir yöntem IDictionary kabul etmesi gereken bir şekilde bildirilirse, ancak çalışma anında gönderen SortedDictionary<TKey,TValue> gönderirse, alıcı gerçekten bir
SortedDictionaryalır (her ne kadar "statik sözleşme"/taneli arabirim bu davranışı belirtmese bile).Nesne kimliğini koruma: Aynı nesne bir taneli çağrının bağımsız değişkenlerinde birden çok kez geçirilirse veya bağımsız değişkenlerden dolaylı olarak birden çok kez işaret edilirse, Orleans bunu yalnızca bir kez serileştirir. Alıcı tarafında, Orleans tüm referansları doğru şekilde geri yükler, böylece seri durumdan çıkarma işleminden sonra aynı nesneye yönelik iki işaretçi hala aynı nesneye işaret eder. Nesne kimliğinin korunması aşağıdaki gibi senaryolarda önemlidir: A diliminin B dilimine 100 giriş içeren bir sözlük gönderdiğini ve sözlükteki 10 anahtarın A tarafında aynı nesneye
objişaret ettiği düşünün. Nesne kimliğini korumadan B, bu 10 anahtarın 10 farklı kopyasına işaret ettiği 100 giriş içerenobjbir sözlük alır. Nesne kimliği korunduğu için, B tarafındaki sözlük A tarafında olduğu gibi görünür ve bu 10 anahtar tek bir nesneyeobjişaret ediyor. .NET'teki varsayılan dize karma kodu uygulamaları işlem başına rastgele olduğundan, sözlüklerdeki ve karma kümelerdeki değerlerin (örneğin) sıralanması korunmayabilir.
Sürüm toleransını desteklemek için serileştirici, hangi türlerin ve üyelerin serileştirildiğini belirtmeniz gerekir. Bunu mümkün olduğunca acısız hale getirmeye çalıştık. Tüm seri hale getirilebilir türleri Orleans.GenerateSerializerAttribute ile işaretleyerek türünüz için Orleans'in seri hale getirici kodu oluşturması talimatını verin. Bunu yaptıktan sonra, burada gösterildiği gibi, türlerinizdeki serileştirilebilir üyelere gerekenleri Orleans.IdAttribute eklemek için dahil edilen kod düzeltmesini kullanabilirsiniz:
Orleans içindeki serileştirilebilir bir türün, özniteliklerin nasıl uygulanacağını gösteren bir örneği burada verilmiştir.
[GenerateSerializer]
public class Employee
{
[Id(0)]
public string Name { get; set; }
}
Orleans devralmayı destekler ve hiyerarşideki tek tek katmanları ayrı ayrı seri hale getirerek ayrı üye kimliklerine sahip olmalarını sağlar.
[GenerateSerializer]
public class Publication
{
[Id(0)]
public string Title { get; set; }
}
[GenerateSerializer]
public class Book : Publication
{
[Id(0)]
public string ISBN { get; set; }
}
Önceki kodda, Publication ve Book'nin üyeleri [Id(0)] olduğunu, BookPublication'den türetilmiş olsa bile, fark edin. Tanımlayıcılar bir bütün olarak türe değil, devralma düzeyine göre belirlendiğinden, bu, Orleans içinde önerilen uygulamadır. Üyeleri PublicationBook bağımsız olarak ekleyip kaldırabilirsiniz, ancak uygulama özel dikkate alınmadan dağıtıldıktan sonra hiyerarşiye yeni bir temel sınıf ekleyemezsiniz.
Orleans, internal, ve private üyelerine sahip türleri serileştirmeyi de destekler. Örneğin, bu örnek tür:
[GenerateSerializer]
public struct MyCustomStruct
{
public MyCustom(int intProperty, int intField)
{
IntProperty = intProperty;
_intField = intField;
}
[Id(0)]
public int IntProperty { get; }
[Id(1)] private readonly int _intField;
public int GetIntField() => _intField;
public override string ToString() => $"{nameof(_intField)}: {_intField}, {nameof(IntProperty)}: {IntProperty}";
}
Varsayılan olarak, Orleans tam adını kodlayarak türünüzü serileştirir.
Orleans.AliasAttribute ekleyerek bunu geçersiz kılabilirsiniz. Temel sınıfın adının değiştirilmesine veya derlemeler arasında taşınmasına karşı dayanıklı olan bir ad kullanılarak türünüzün serileştirilmesiyle sonuçlanır. Tip takma adları küresel kapsamlıdır ve bir uygulamada aynı değere sahip iki takma ada sahip olamazsınız. Genel türler için diğer ad değeri, ters tırnak işaretiyle belirlenen genel parametrelerin sayısını içermelidir; örneğin, MyGenericType<T, U> diğer adına [Alias("mytype`2")] sahip olabilir.
record türlerini serileştirme
Kaydın birincil oluşturucusunda tanımlanan bir üye, varsayılan olarak örtük bir kimliğe sahiptir. Başka bir deyişle, Orleans türleri serileştirmeyi record destekler. Bu, uygulamanızın önceki sürümleriyle (sıralı yükseltme senaryosunda) ve depolama ve akışlarda söz konusu türün serileştirilmiş örnekleriyle uyumluluğu bozan, zaten dağıtılmış bir türün parametre sırasını değiştiremeyeceğiniz anlamına gelir. Kayıt türünün gövdesinde tanımlanan üyeler kimlikleri birincil oluşturucu parametreleriyle paylaşmaz.
[GenerateSerializer]
public record MyRecord(string A, string B)
{
// ID 0 won't clash with A in primary constructor as they don't share identities
[Id(0)]
public string C { get; init; }
}
Birincil oluşturucu parametrelerinin otomatik olarak serileştirilebilir alanlar olarak eklenmesini istemiyorsanız kullanın [GenerateSerializer(IncludePrimaryConstructorParameters = false)].
Yabancı türleri seri hale getirme vekilleri
Bazen, üzerinde tam denetime sahip olmadığınız tanecikler arasında türleri geçirmeniz gerekebilir. Böyle durumlarda, uygulama kodunuzda özel tanımlı bir türe manuel dönüştürme pratik olmayabilir. Orleans bu durumlar için bir çözüm sunar: vekil türler. Vekiller, hedef türleri yerine serileştirilir ve hedef türe ve hedef türe dönüştürme işlevlerine sahiptir. Aşağıdaki yabancı tür ve karşılık gelen vekil ve dönüştürücü örneğini göz önünde bulundurun:
// This is the foreign type, which you do not have control over.
public struct MyForeignLibraryValueType
{
public MyForeignLibraryValueType(int num, string str, DateTimeOffset dto)
{
Num = num;
String = str;
DateTimeOffset = dto;
}
public int Num { get; }
public string String { get; }
public DateTimeOffset DateTimeOffset { get; }
}
// This is the surrogate which will act as a stand-in for the foreign type.
// Surrogates should use plain fields instead of properties for better performance.
[GenerateSerializer]
public struct MyForeignLibraryValueTypeSurrogate
{
[Id(0)]
public int Num;
[Id(1)]
public string String;
[Id(2)]
public DateTimeOffset DateTimeOffset;
}
// This is a converter that converts between the surrogate and the foreign type.
[RegisterConverter]
public sealed class MyForeignLibraryValueTypeSurrogateConverter :
IConverter<MyForeignLibraryValueType, MyForeignLibraryValueTypeSurrogate>
{
public MyForeignLibraryValueType ConvertFromSurrogate(
in MyForeignLibraryValueTypeSurrogate surrogate) =>
new(surrogate.Num, surrogate.String, surrogate.DateTimeOffset);
public MyForeignLibraryValueTypeSurrogate ConvertToSurrogate(
in MyForeignLibraryValueType value) =>
new()
{
Num = value.Num,
String = value.String,
DateTimeOffset = value.DateTimeOffset
};
}
Önceki kodda:
-
MyForeignLibraryValueType, denetiminizin dışında, tüketen bir kitaplıkta tanımlanan bir türdür. -
MyForeignLibraryValueTypeSurrogateveMyForeignLibraryValueTypearasında eşleme yapan bir yedek türdür. -
RegisterConverterAttribute,
MyForeignLibraryValueTypeSurrogateConverter'in iki türü eşlemek için dönüştürücü olarak işlediğini belirtir. sınıfı arabirimini IConverter<TValue,TSurrogate> uygular.
Orleans tür hiyerarşilerindeki türlerin serileştirilmesini destekler (diğer türlerden türetilen türler). Yabancı tür bir tip hiyerarşisinde görünebilirse (örneğin, kendi türlerinizden birinin temel sınıfı olarak), arabirimi ek olarak Orleans.IPopulator<TValue,TSurrogate> uygulamanız gerekir. Aşağıdaki örneği inceleyin:
// The foreign type is not sealed, allowing other types to inherit from it.
public class MyForeignLibraryType
{
public MyForeignLibraryType() { }
public MyForeignLibraryType(int num, string str, DateTimeOffset dto)
{
Num = num;
String = str;
DateTimeOffset = dto;
}
public int Num { get; set; }
public string String { get; set; }
public DateTimeOffset DateTimeOffset { get; set; }
}
// The surrogate is defined as it was in the previous example.
[GenerateSerializer]
public struct MyForeignLibraryTypeSurrogate
{
[Id(0)]
public int Num;
[Id(1)]
public string String;
[Id(2)]
public DateTimeOffset DateTimeOffset;
}
// Implement the IConverter and IPopulator interfaces on the converter.
[RegisterConverter]
public sealed class MyForeignLibraryTypeSurrogateConverter :
IConverter<MyForeignLibraryType, MyForeignLibraryTypeSurrogate>,
IPopulator<MyForeignLibraryType, MyForeignLibraryTypeSurrogate>
{
public MyForeignLibraryType ConvertFromSurrogate(
in MyForeignLibraryTypeSurrogate surrogate) =>
new(surrogate.Num, surrogate.String, surrogate.DateTimeOffset);
public MyForeignLibraryTypeSurrogate ConvertToSurrogate(
in MyForeignLibraryType value) =>
new()
{
Num = value.Num,
String = value.String,
DateTimeOffset = value.DateTimeOffset
};
public void Populate(
in MyForeignLibraryTypeSurrogate surrogate, MyForeignLibraryType value)
{
value.Num = surrogate.Num;
value.String = surrogate.String;
value.DateTimeOffset = surrogate.DateTimeOffset;
}
}
// Application types can inherit from the foreign type, assuming they're not sealed
// since Orleans knows how to serialize it.
[GenerateSerializer]
public sealed class DerivedFromMyForeignLibraryType : MyForeignLibraryType
{
public DerivedFromMyForeignLibraryType() { }
public DerivedFromMyForeignLibraryType(
int intValue, int num, string str, DateTimeOffset dto) : base(num, str, dto)
{
IntValue = intValue;
}
[Id(0)]
public int IntValue { get; set; }
}
Sürüm oluşturma kuralları
Türleri değiştirirken bir dizi kuralı izlemeniz koşuluyla sürüm toleransı desteklenir. Google Protokol Arabellekleri (Protobuf) gibi sistemleri biliyorsanız, bu kurallar tanıdık olacaktır.
Bileşik türler (class & struct)
- Devralma desteklenir, ancak bir nesnenin devralma hiyerarşisinde değişiklik yapmak desteklenmez. Bir sınıfın temel sınıfını ekleyemez, değiştiremez veya kaldıramazsınız.
- Aşağıdaki Sayısallar bölümünde açıklanan bazı sayısal türler dışında, alan türlerini değiştiremezsiniz.
- Devralma hiyerarşisinde herhangi bir noktada alan ekleyebilir veya kaldırabilirsiniz.
- Alan kimliklerini değiştiremezsiniz.
- Alan kimlikleri bir tür hiyerarşisindeki her düzey için benzersiz olmalıdır, ancak temel sınıflar ve alt sınıflar arasında yeniden kullanılabilir. Örneğin, bir
Basesınıf kimliğine0sahip bir alan bildirebilir ve birSub : Basesınıf da aynı kimliğe0sahip farklı bir alan bildirebilir.
Sayısal veriler
- Sayısal alanın imzalılığını değiştiremezsiniz.
- arasındaki
intuintdönüştürmeler geçersiz.
- arasındaki
- Sayısal alanın genişliğini değiştirebilirsiniz.
- Örneğin,
int'denlong'e veyaulong'denushort'e dönüştürmeler desteklenir. - Alanın çalışma zamanı değeri taşma neden olursa, genişliği daraltan dönüştürmeler bir özel durum oluşturur.
-
ulong'danushort'e dönüştürme yalnızca çalışma zamanı değeriushort.MaxValue'den küçükse desteklenir. -
double'denfloat'e dönüştürmeler, yalnızca çalışma zamanı değerifloat.MinValueilefloat.MaxValuearasında olduğunda desteklenir. - Benzer şekilde,
decimal, hemdoublehem defloatile karşılaştırıldığında daha dar bir aralığa sahiptir.
- Örneğin,
Fotokopi
Orleans bazı eşzamanlılık hatası sınıflarına karşı korumayı da içeren güvenliği varsayılan olarak sağlar. Özellikle, Orleans varsayılan olarak grain çağrılarında geçirilen nesneleri hemen kopyalar. Orleans. Serileştirme bu kopyalamayı kolaylaştırır. Bir türe uyguladığınızda Orleans.CodeGeneration.GenerateSerializerAttribute , Orleans bu tür için de kopyalayıcılar oluşturur. Orleans , ile işaretlenmiş ImmutableAttributetürleri veya tek tek üyeleri kopyalamaktan kaçınıyor. Daha fazla ayrıntı için bkz . içindeki Orleanssabit türleri seri hale getirme.
Serileştirme en iyi yöntemleri
✅ özniteliğini kullanarak türlerinize diğer adlar
[Alias("my-type")]verin. Diğer adlara sahip türler, uyumsuzluğa neden olmadan yeniden adlandırılabilir.❌ Normal bir
recorddeğeriniclassveya tam tersi olarak değiştirmeyin. Kayıtlar, normal üyelere ek olarak birincil oluşturucu üyelerine sahip olduğundan kayıtlar ve sınıflar aynı şekilde temsil değildir; bu nedenle ikisi birbirinin yerine kullanılamaz.❌ Serileştirilebilir bir tür için var olan bir tür hiyerarşisine yeni türler eklemeyin. Var olan bir türe yeni bir temel sınıf eklememelisiniz. Mevcut bir türe güvenli bir şekilde yeni bir alt sınıf ekleyebilirsiniz.
✅ kullanımlarını SerializableAttribute ve buna karşılık gelen GenerateSerializerAttribute bildirimlerle IdAttribute değiştirin.
✅Her tür için tüm üye kimliklerini sıfırdan başlatın. Bir alt sınıftaki ve temel sınıfındaki kimlikler güvenli bir şekilde çakışabilir. Aşağıdaki örnekteki her iki özelliğin de kimlikleri
0ile aynıdır.[GenerateSerializer] public sealed class MyBaseClass { [Id(0)] public int MyBaseInt { get; set; } } [GenerateSerializer] public sealed class MySubClass : MyBaseClass { [Id(0)] public int MyBaseInt { get; set; } }✅ Gerektiğinde sayısal üye türlerini genişletme. olarak genişletebilirsiniz
sbyteshortintlong.- Sayısal üye türlerini daraltabilirsiniz, ancak gözlemlenen değerler daraltılmış tür tarafından doğru şekilde temsil edilemiyorsa bu, çalışma zamanı hatasıyla sonuçlanır. Örneğin,
int.MaxValuebirshortalan tarafından temsil edilemez, bu nedenle birintalanınshortdaraltılması, böyle bir değerle karşılaşılırsa çalışma zamanı özel durumuyla sonuçlanabilir.
- Sayısal üye türlerini daraltabilirsiniz, ancak gözlemlenen değerler daraltılmış tür tarafından doğru şekilde temsil edilemiyorsa bu, çalışma zamanı hatasıyla sonuçlanır. Örneğin,
❌ Sayısal tür üyesinin imzalılığını değiştirmeyin. Örneğin, bir üyenin türünü
uintintolarak veyaintuintolarak değiştirmemelisiniz.
Tahıl depolama serileştiricileri
Orleans özelliği aracılığıyla State erişilen veya tahılınıza bir veya daha fazla IPersistentState<TState> değer eklenerek tanecikler için sağlayıcı destekli kalıcılık modeli içerir. 7.0'ın öncesinde Orleans her sağlayıcının serileştirmeyi yapılandırmak için farklı bir mekanizması vardı. 7.0'da Orleans , her sağlayıcı için durum serileştirmesini özelleştirmek için tutarlı bir yol sunan genel amaçlı bir tanecik durum serileştirici arabirimi IGrainStorageSerializervardır. Desteklenen depolama sağlayıcıları, sağlayıcının IStorageProviderSerializerOptions.GrainStorageSerializer seçenekler sınıfında özelliği ayarlamayı içeren bir desen uygular, örneğin:
- DynamoDBStorageOptions.GrainStorageSerializer
- AzureBlobStorageOptions.GrainStorageSerializer
- AzureTableStorageOptions.GrainStorageSerializer
- GrainStorageSerializer
Tahıl depolama serileştirmesi şu anda durumu seri hale getirmek için varsayılan olarak Newtonsoft.Json ayarlanmıştır. Yapılandırma zamanında bu özelliği değiştirerek bunu değiştirebilirsiniz. Aşağıdaki örnekte OptionsBuilder<TOptions kullanılarak bu gösterilmektedir>:
siloBuilder.AddAzureBlobGrainStorage(
"MyGrainStorage",
(OptionsBuilder<AzureBlobStorageOptions> optionsBuilder) =>
{
optionsBuilder.Configure<IMySerializer>(
(options, serializer) => options.GrainStorageSerializer = serializer);
});
Daha fazla bilgi için bkz . OptionsBuilder API'si.
Orleans gelişmiş ve genişletilebilir bir serileştirme çerçevesine sahiptir. Orleans hem taneli istek ve yanıt iletilerinde geçirilen veri türlerini hem de taneli kalıcı durum nesnelerini serileştirir. Bu çerçevenin bir parçası olarak, Orleans bu veri türleri için otomatik olarak serileştirme kodu oluşturur. .NET-serializable olan türler için daha verimli serileştirme/seri durumdan çıkarma oluşturmanın yanı sıra, Orleans .NET-serializable olmayan ve tanecik arabirimlerinde kullanılan türler için de serileştiriciler oluşturmaya çalışır. Çerçeve ayrıca sık kullanılan türler için etkili bir dizi yerleşik serileştirici içerir: listeler, sözlükler, dizeler, ilkel öğeler, diziler vb.
' seri hale getiricisinin Orleansiki önemli özelliği onu diğer birçok üçüncü taraf serileştirme çerçevesinden ayırır: dinamik türler/rastgele polimorfizm ve nesne kimliği.
Dinamik türler ve rastgele polimorfizm: Orleans grain çağrılarında geçirilen türlerde kısıtlamaları uygulamaz ve gerçek veri türünün dinamik doğasını korur. Bu, şu anlama gelir ki, örneğin bir taneli arabirimdeki bir yöntem IDictionary kabul etmesi gereken bir şekilde bildirilirse, ancak çalışma anında gönderen SortedDictionary<TKey,TValue> gönderirse, alıcı gerçekten bir
SortedDictionaryalır (her ne kadar "statik sözleşme"/taneli arabirim bu davranışı belirtmese bile).Nesne kimliğini koruma: Aynı nesne bir taneli çağrının bağımsız değişkenlerinde birden çok kez geçirilirse veya bağımsız değişkenlerden dolaylı olarak birden çok kez işaret edilirse, Orleans bunu yalnızca bir kez serileştirir. Alıcı tarafında, Orleans tüm referansları doğru şekilde geri yükler, böylece seri durumdan çıkarma işleminden sonra aynı nesneye yönelik iki işaretçi hala aynı nesneye işaret eder. Nesne kimliğinin korunması aşağıdaki gibi senaryolarda önemlidir: A diliminin B dilimine 100 giriş içeren bir sözlük gönderdiğini ve sözlükteki 10 anahtarın A tarafında aynı nesneye
objişaret ettiği düşünün. Nesne kimliğini korumadan B, bu 10 anahtarın 10 farklı kopyasına işaret ettiği 100 giriş içerenobjbir sözlük alır. Nesne kimliği korunduğu için, B tarafındaki sözlük A tarafında olduğu gibi görünür ve bu 10 anahtar tek bir nesneyeobjişaret ediyor.
Standart .NET ikili seri hale getirici yukarıdaki iki davranışı sağlar, bu nedenle bu standart ve tanıdık davranışı Orleans da desteklememiz önemlidir.
Oluşturulan serileştiriciler
Orleans hangi serileştiricilerin oluşturulacağını belirlemek için aşağıdaki kuralları kullanır:
- Çekirdek Orleans kitaplığına başvuran tüm derlemelerdeki tüm türleri tarayın.
- Bu derlemelerden, doğrudan taneli arabirim yöntemi imzalarında veya durum sınıfı imzalarında başvurulan türler için ya da SerializableAttribute ile işaretlenmiş herhangi bir tür için serileştiriciler oluşturun.
- Ayrıca, bir taneli arabirim veya uygulama projesi, serileştirme oluşturma için rastgele türleri işaret etmek amacıyla KnownTypeAttribute veya KnownAssemblyAttribute derleme düzeyi öznitelikleri ekleyebilir. Bunlar, kod oluşturucuya belirli türler veya bir derleme içindeki tüm uygun türler için serileştiriciler oluşturmasını söyler. Derleme düzeyi öznitelikleri hakkında daha fazla bilgi için Derleme Düzeyinde Öznitelik Uygulama konusuna bakın.
Yedek serileştirme
Orleans çalışma zamanında rastgele türlerin iletimini destekler. Bu nedenle, yerleşik kod oluşturucu önceden iletilecek tür kümesinin tamamını belirleyemez. Ayrıca, erişilemeyen (örn. private) veya erişilemeyen alanlara (örn. readonly) sahip oldukları için bazı türler için seri hale getirici oluşturulamaz. Bu nedenle, beklenmeyen veya önceden seri hale getiricileri oluşturulamayan türlerin tam zamanında seri hale getirilmesi gerekir. Bu türlerden sorumlu seri hale getiriciye geri dönüş serileştiricisi adı verilir.
Orleans iki yedek serileştirici ile birlikte:
- Orleans.Serialization.BinaryFormatterSerializer, .NET'in BinaryFormatter'ini kullanır; ve
-
Orleans.Serialization.ILBasedSerializer, her bir alanı seri hale getirmek için 'nin serileştirme çerçevesinden yararlanan Orleans serileştiriciler oluşturmak üzere çalışma zamanında CIL yönergelerini üretir. Bu, erişilemeyen bir türün
MyPrivateTypeözel bir seri hale getiriciye sahip bir alanMyTypeiçerdiği durumlarda, bu özel seri hale getiricinin o alanı seri hale getirmek için kullanılacağı anlamına gelir.
Hem FallbackSerializationProvider (istemci) hem de ClientConfiguration (silo) üzerinde GlobalConfiguration özelliğini kullanarak geri dönüş serileştiricisini yapılandırın.
// Client configuration
var clientConfiguration = new ClientConfiguration();
clientConfiguration.FallbackSerializationProvider =
typeof(FantasticSerializer).GetTypeInfo();
// Global configuration
var globalConfiguration = new GlobalConfiguration();
globalConfiguration.FallbackSerializationProvider =
typeof(FantasticSerializer).GetTypeInfo();
Alternatif olarak, XML yapılandırmasında geri dönüş serileştirme sağlayıcısını belirtin:
<Messaging>
<FallbackSerializationProvider
Type="GreatCompany.FantasticFallbackSerializer, GreatCompany.SerializerAssembly"/>
</Messaging>
BinaryFormatterSerializer varsayılan yedek serileştiricidir.
Uyarı
ile BinaryFormatter ikili serileştirme tehlikeli olabilir. Daha fazla bilgi için BinaryFormatter güvenlik kılavuzuna ve BinaryFormatter geçiş kılavuzuna bakın.
Özel durum serileştirme
Özel durumlar yedek serileştirici kullanılarak serileştirilir. Varsayılan yapılandırmada BinaryFormatter yedek serileştiricidir. Bu nedenle, bir özel durum türündeki tüm özelliklerin doğru seri hale getirilmesini sağlamak için ISerializable desenini izlemeniz gerekir.
Aşağıda, doğru şekilde uygulanan serileştirmeye sahip bir özel durum türü örneği verilmiştir:
[Serializable]
public class MyCustomException : Exception
{
public string MyProperty { get; }
public MyCustomException(string myProperty, string message)
: base(message)
{
MyProperty = myProperty;
}
public MyCustomException(string transactionId, string message, Exception innerException)
: base(message, innerException)
{
MyProperty = transactionId;
}
// Note: This is the constructor called by BinaryFormatter during deserialization
public MyCustomException(SerializationInfo info, StreamingContext context)
: base(info, context)
{
MyProperty = info.GetString(nameof(MyProperty));
}
// Note: This method is called by BinaryFormatter during serialization
public override void GetObjectData(SerializationInfo info, StreamingContext context)
{
base.GetObjectData(info, context);
info.AddValue(nameof(MyProperty), MyProperty);
}
}
Serileştirme en iyi yöntemleri
Serileştirme, içinde Orleansiki birincil amaca hizmet eder:
- Çalışma zamanında tahıllar ve istemciler arasında veri iletmek için bir kablo biçimi olarak.
- Daha sonra almak üzere uzun ömürlü verileri kalıcı olarak saklamak için bir depolama biçimi olarak.
tarafından Orleans oluşturulan serileştiriciler esneklik, performans ve çok yönlülüklerinden dolayı ilk amaca uygundur. Bunlar, sürüm-toleransı açıkça olmadığından ikinci amaç için o kadar uygun değildir. Kalıcı veriler için Protokol Arabellekleri gibi sürüme dayanıklı bir seri hale getirici yapılandırmanızı öneririz. Protokol Arabellekleri, Orleans.Serialization.ProtobufSerializer ile Orleans NuGet paketi aracılığıyla desteklenir. Sürüm toleransını sağlamak için seçtiğiniz seri hale getirici için en iyi yöntemleri izleyin. Yukarıda açıklandığı gibi yapılandırma özelliğini kullanarak SerializationProviders üçüncü taraf seri hale getiricileri yapılandırın.