vendredi 18 janvier 2019

.Net Framework mscorlib.dll GetProperty causes an error because of its cache while serialize an object by using Microsoft.Core.Avro

I don't know how to explain this problem really.

I'm using Microsoft.Core.Avro.dll. I downloaded from Nuget Package Manager, it's on https://github.com/dougmsft/microsoft-avro.

I made a simple application. I tried to create a lot of case for explaining the problem. It gives an error when I deserialize an object that is serialized after try to get property of Type by using GetProperty. I think that It is related with string type property. I want to share the code here but it is a little longer. I share just few case here. I share all case with my application.

https://ufile.io/6xf9a

    [Test]
    public static void Test7()
    {
        // this throws an exception that is 'Unexpected end of stream: '17' bytes missing.'
        var f = new Foo7 { P1 = 1, P2 = 2, PP2 = 22, P3 = "test" };

        PropertyInfo p1 = f.GetType().GetProperty("P1");
        PropertyInfo p2 = f.GetType().GetProperty("P2");
        PropertyInfo p3 = f.GetType().GetProperty("P22");
        PropertyInfo p4 = f.GetType().GetProperty("P3");
        Stream s1 = Helper.Serialize(f);
        var s2 = Helper.Deserialize<Foo7>(s1);
        Assert.True(Helper.Equal(f, s2));
    }

    [Test]
    public static void Test7_1()
    {
        // Assert returns false, These objects are not the same.
        var f = new Foo7_1 { P1 = 1, P2 = 2, PP2 = 3, P3 = "test" };

        PropertyInfo p1 = f.GetType().GetProperty("P1");
        PropertyInfo p2 = f.GetType().GetProperty("P2");
        PropertyInfo p3 = f.GetType().GetProperty("P22");
        PropertyInfo p4 = f.GetType().GetProperty("P3");
        Stream s1 = Helper.Serialize(f);
        var s2 = Helper.Deserialize<Foo7_1>(s1);
        Assert.True(Helper.Equal(f, s2));
    }

    [Test]
    public static void Test7_2()
    {
        // Assert returns true. This is correct.
        var f = new Foo7_2 { P1 = 1, P2 = 2, PP2 = 22, P3 = "test" };

        var x = typeof(Foo7_2).GetProperties().ToList();

        PropertyInfo p1 = f.GetType().GetProperty("P1");
        PropertyInfo p2 = f.GetType().GetProperty("P2");
        PropertyInfo p3 = f.GetType().GetProperty("P22");
        PropertyInfo p4 = f.GetType().GetProperty("P3");
        Stream s1 = Helper.Serialize(f);
        var s2 = Helper.Deserialize<Foo7_2>(s1);
        Assert.True(Helper.Equal(f, s2));
    }

    public class Foo7
{
    public int P1 { get; set; }
    public long P2 { get; set; }
    public long PP2 { get; set; }
    public string P3 { get; set; }
}


public class Foo7_1
{
    public int P1 { get; set; }
    public long P2 { get; set; }
    public long PP2 { get; set; }
    public string P3 { get; set; }
}

public class Foo7_2
{
    public int P1 { get; set; }
    public long P2 { get; set; }
    public long PP2 { get; set; }
    public string P3 { get; set; }
}

// https://github.com/dougmsft/microsoft-avro
    public static Stream Serialize<T>(T obj)
    {
        if (obj == null) return null;
        var avroSerializerSettings = new AvroSerializerSettings
                                     {
                                         GenerateDeserializer = false,
                                         GenerateSerializer = true,
                                         Resolver = new AvroPublicMemberContractResolver(),
                                         UsePosixTime = false,
                                         KnownTypes = new List<Type> { typeof(T) },
                                         UseCache = true,
                                         Surrogate = null
                                     };

        IAvroSerializer<T> avroSerializer = AvroSerializer.Create<T>(avroSerializerSettings);
        var mem = new MemoryStream();
        avroSerializer.Serialize(mem, obj);
        return new MemoryStream(mem.ToArray());
    }

    public static T Deserialize<T>(Stream stream)
    {
        stream.Position = 0;
        var avroSerializerSettings = new AvroSerializerSettings
                                     {
                                         GenerateDeserializer = true,
                                         GenerateSerializer = false,
                                         Resolver = new AvroPublicMemberContractResolver(),
                                         UsePosixTime = false,
                                         KnownTypes = new List<Type> { typeof(T) },
                                         UseCache = true,
                                         Surrogate = null
                                     };

        IAvroSerializer<T> avroSerializer = AvroSerializer.Create<T>(avroSerializerSettings);
        T o = avroSerializer.Deserialize(stream);
        return o;
    }

        public static bool Equal(Foo7 t1, Foo7 t2)
    {
        if (t1.P1 != t2.P1) return false;
        if (t1.P2 != t2.P2) return false;
        if (t1.PP2 != t2.PP2) return false;
        if (t1.P3 != t2.P3) return false;

        return true;
    }

    public static bool Equal(Foo7_1 t1, Foo7_1 t2)
    {
        if (t1.P1 != t2.P1) return false;
        if (t1.P2 != t2.P2) return false;
        if (t1.PP2 != t2.PP2) return false;
        if (t1.P3 != t2.P3) return false;

        return true;
    }

    public static bool Equal(Foo7_2 t1, Foo7_2 t2)
    {
        if (t1.P1 != t2.P1) return false;
        if (t1.P2 != t2.P2) return false;
        if (t1.PP2 != t2.PP2) return false;
        if (t1.P3 != t2.P3) return false;

        return true;
    }





Aucun commentaire:

Enregistrer un commentaire