title: System.Text.Json Deserialize nested object from API call - Data is wrapped in parent JSON property
body: <p>
  I have an API JSON response that wraps the data content in a <code>data</code> property, which looks like this:</p>
  
  <pre class="lang-cs prettyprint-override"><code>{ 
     "data":{ 
        "email":"admin@example.com",
        "mobile":"+1555555123",
        "id":4,
        "first_name":"Merchant",
        "last_name":"Vendor",
        "role":"Merchant",
     }
  }
  </code></pre>
  
  <p>So when making request for a User Object with a Library like <code>RequestSharp</code>, the <code>response.Content</code> has the content for the User wrapped in the <code>data</code> json property as it comes from the API. Code:</p>
  
  <pre class="lang-cs prettyprint-override"><code>var request = RequestHelper.CreateTokenRequest(email, password); // Create the request from a helper
  var client = new RestClient(BaseUrl); // create new RestSharp Client
  IRestResponse response = client.Execute(request); // execute the request
  var content = response.Content; // raw content as string
  </code></pre>
  
  <p>This is fine, but when I go to deserialize the json to an Object with <code>System.Text.Json</code>, like the following, will create the <code>User</code> object but will not assign any of the attributes, although this is sort of expected because the serializer is looking for properties with <code>first_name</code> and <code>last_name</code>... not <code>['data']['first_name']</code></p>
  
  <pre class="lang-cs prettyprint-override"><code>User account = JsonSerializer.Deserialize&lt;User&gt;(response.Content, options);
  
  </code></pre>
  
  <p>How can I get the <code>JsonSerializer.Deserialize</code> to ignore the <code>data</code> wrapper? In other API calls it may be the name of the Object such as <code>transaction</code> or <code>user</code>, either way, it wraps the data.</p>
  
  <p>Other Notes:</p>
  
  <p>I am targeting the latest .Net Core 3.1 and am migrating from Newtonsoft Json.Net</p>
  
  <hr>
  
  <p>My User Object:</p>
  
  <pre class="lang-cs prettyprint-override"><code>using System.ComponentModel;
  using System.Text.Json.Serialization;
  
  namespace MyApplication.Models
  {
      public interface IUser
      {
          string FirstName { get; set; }
          string LastName { get; set; }
          string Email { get; set; }
          string Mobile { get; set; }
          string Id { get; set; }
          string Role { get; set; }
      }
  
      public class User : IUser
      {
          [JsonPropertyName("first_name")]
          public string FirstName { get; set; }
  
          [JsonPropertyName("last_name")]
          public string LastName { get; set; }
  
          [JsonPropertyName("email")]
          public string Email { get; set; }
  
          [JsonPropertyName("mobile")]
          public string Mobile { get; set; }
  
          [JsonPropertyName("id")]
          public string Id { get; set; }
  
          [JsonPropertyName("role")]
          public string Role { get; set; }
  
          [JsonIgnore]
          public string Token { get; set; }
      }
  }
  
  </code></pre>
  
  <hr>
  
  <p>Update after resolution:</p>
  
  <p>I selected the answer from u/Nikunj Kakadiya below as something that would work and was most similar to what I ended up doing. </p>
  
  <p>I created a generic template based container class to handle the <code>data</code> like this:</p>
  
  <pre class="lang-cs prettyprint-override"><code>public class Container&lt;T&gt;
  {
      [JsonPropertyName("data")]
      public T Data { get; set; }
  }
  </code></pre>
  
  <p>I then used that container class to wrap the returned json contents from the API call, like this:</p>
  
  <pre class="lang-cs prettyprint-override"><code>var options = new JsonSerializerOptions
  {
      AllowTrailingCommas = true
  };
  
  Container&lt;User&gt; accountContainer = JsonSerializer.Deserialize&lt;Container&lt;User&gt;&gt;(response.Content, options);
  User account = accountContainer.Data;
  </code></pre>
  
  <p>Additionally, as u/Pavel Anikhouski noted, my serialization of the <code>User</code> class led to an error that required me to create a custom converter for the <code>id</code> field. The API returns the <code>id</code> as an integer although it is a string in the <code>User</code> class. This was the error I ran into which was initially confusing but I was able to figure out pretty quickly: <code>ERROR: The JSON value could not be converted to System.String. Path: $.data.id | LineNumber: 0 | BytePositionInLine: 77.</code> </p>
  
  <p>Here is the custom converter <code>IntToStringConverter</code>:</p>
  
  <pre class="lang-cs prettyprint-override"><code>public class IntToStringConverter : JsonConverter&lt;string&gt;
  {
      public override string Read(
          ref Utf8JsonReader reader,
          Type typeToConvert,
          JsonSerializerOptions options) =&gt; reader.GetInt32().ToString();
  
      public override void Write(
          Utf8JsonWriter writer,
          string value,
          JsonSerializerOptions options) =&gt;
          writer.WriteStringValue(value);
  }
  </code></pre>
  
  <p>and then changed the <code>User</code> Class to use the customer converter:</p>
  
  <pre class="lang-cs prettyprint-override"><code>...
      [JsonPropertyName("id")]
      [JsonConverter(typeof(IntToStringConverter))]
      public string Id { get; set; }
  ...
  </code></pre>