0

In this lecture about Json Schemas we can validate that a json array has specific types for specific indices (it's called tuple there). For example a tuple for an street address:

[NUMBER, STREET_NAME, STREET_TYPE, DIRECTION] // Structure
[1600, "Pennsylvania", "Avenue", "NW"] // Example

where the different items in this (fixed length) array mean:

  • (int) NUMBER: The address number.
  • (string) STREET_NAME: The name of the street.
  • (enum) STREET_TYPE: The type of street. Can be Street, Avenue or Boulevard.
  • (enum) DIRECTION: The city quadrant of the address. Can be NW, NE, SW or SE.

What is a clean way of deserializing such an array using Newtonsofts Json.Net? The model should look like:

public class StreetAddress
{
    public int Number { get; set; }
    public string StreetName { get; set; }
    public StreetType StreetType { get; set; }
    public Direction Direction { get; set; }
}

public enum StreetType
{
    Street,
    Avenue,
    Boulevard
}

public enum Direction
{
    Nw,
    Ne,
    Sw,
    Se
}

Are there attributes to define the ordinal indices for each property or an attribute for using an e.g. ArrayConverter for the whole model? Well, we could just use a JArray und assign each property from an index, but that does not feel very smooth.

Bruno Zell
  • 7,761
  • 5
  • 38
  • 46

1 Answers1

0

This is how I would set up your data class StreetAddress:

public class StreetAddress
{
    [JsonProperty(Order = 1)]
    public Int32 Number { get; set; }

    [JsonProperty(Order = 2)]
    public String StreetName { get; set; }

    [JsonProperty(Order = 3)]
    [JsonConverter(typeof(StringEnumConverter))]
    public StreetType StreetType { get; set; }

    [JsonProperty(Order = 3)]
    [JsonConverter(typeof(StringEnumConverter))]
    public Direction Direction { get; set; }
}

Then you have to implement the proper conversion type of your enumerators using StringEnumConverter:

[JsonConverter(typeof(StringEnumConverter))]
public enum StreetType
{
    [EnumMember(Value = "Street")]
    Street,
    [EnumMember(Value = "Avenue")]
    Avenue,
    [EnumMember(Value = "Boulevard")]
    Boulevard
}

[JsonConverter(typeof(StringEnumConverter))]
public enum Direction
{
    [EnumMember(Value = "Nw")]
    Nw,
    [EnumMember(Value = "Ne")]
    Ne,
    [EnumMember(Value = "Sw")]
    Sw,
    [EnumMember(Value = "Se")]
    Se
}

This should be enough to parse your data.

Tommaso Belluzzo
  • 23,232
  • 8
  • 74
  • 98
  • But that still would requre that the tuple is an json object (`{...}`), not an json array (`[...]`). It would also serialize it into an object with property names specified. – Bruno Zell Dec 24 '17 at 19:56
  • What I need is a way to represent the data in json as an array with no property names specified (instead use the ordinal index), but the object model will have the property names specified (so (de)serializing using the ordinal index) – Bruno Zell Dec 24 '17 at 19:57
  • I think that this transformation is better suited to be performed after the initial parsing. If you give me a concrete example of the desired output I can modify my answer, – Tommaso Belluzzo Dec 24 '17 at 23:58