lundi 17 octobre 2016

Fill dynamically object properties from bytes

I have a list of byte packets and I want to parse them into a list of objects.

There are many different types of objects and every type can have different properties. I'm trying to find some elegant way to fill the properties of each object. I declared all types of objects, and I added some custom attributes in each property that has the offset, the number of bytes of this property in the packet and the type of the property (numeric, string, date...) The first byte of every packet declares the type of the object so I created an attribute for each object type, so if the first byte is 'A' I must create an TypeA object.

//{ 'A'| property1 is 4 bytes | property2 8 bytes }
[PacketType(type: 'A')]
 class TypeA : GenericType
 {
  [Field(FieldType.Numeric, 1, 4)] //4 bytes starting from 1
  public int Property1 { get; set; }

  [Field(FieldType.Numeric, 5, 8)]//8 bytes starting from 5
  public long Property2 { get; set; }
}

[PacketType(type: 'B')] 
class TypeB :GenericType 
{
  [Field(FieldType.Numeric, 1, 2)]
  public int Property4 { get; set; }

  [Field(FieldType.String, 3, 8)]
  public string Property5 { get; set; }

  //other properties
  //...
}

 //
 // many other types 
 //...
 //...
 //...

[AttributeUsage(AttributeTargets.Class)]
public class PacketType : Attribute
{
  public PacketType(char type)
  {

  }
}

[AttributeUsage(AttributeTargets.Property)]
public class Field : Attribute
{
  public Field(FieldType type, int offset, int length)
  {

  }
}

public enum FieldType
{
   Numeric,
   String
}

So I want to implement a method that returns an object of the specific type

  public GenericType Parse(byte[] packet)
  {
     char type = (char)packet[0];
     //find the object type I must create 

    var allTypes = Assembly.GetExecutingAssembly().GetTypes().Where(t => typeof(GenericType).IsAssignableFrom(t) && !t.IsAbstract).ToList();

     // foreach property property of the object
     // {
     //  get the offset and length from the attributes and set the value from the bytes
     // }

     return ..;
  }

Thank you





Aucun commentaire:

Enregistrer un commentaire