Access Cosmos Db JSON data using C# MVC

305 Views Asked by At

I am trying to display Cosmos db JSON Subitems using c# MVC Web application. But I am getting an error:

Could not cast or convert from System.DateTime to WebApplication1.Models.Entry.

JSON:

 "DataTypeId": 1,
"IPaddress": "192.168.2.177",
"id": "d1b81653-b7a5-4d79-85ea-79c01f43f747",
"PhoneNo": "0417518324",
"LastContact": {
    "EnvLog": "2019-09-07T19:41:08",
    "Ping": "2020-01-09T12:10:09",
    "SpdLog": "2019-09-07T19:41:08"
},
"SpeedLog": true,
"DeviceModelId": 2,
"DisconnectEvents": 9,

Model:

    public class DeviceMap
{

    [JsonProperty(PropertyName = "id")]
    public string Id { get; set; }

    [JsonProperty(PropertyName = "IPaddress")]
    public string IPaddress { get; set; }

    [JsonProperty(PropertyName = "SpeedLog")]
    public bool SpeedLog { get; set; }

    [JsonProperty(PropertyName = "LastContact")]
    public Entry LastContact { get; set; }
}

 public class Entry

{

    [JsonProperty(PropertyName = "EnvLog")]
    public DateTime EnvLogtime { get; set; }

    [JsonProperty(PropertyName = "Ping")]
    public DateTime Ping { get; set; }

    [JsonProperty(PropertyName = "SpdLog")]
    public DateTime SpdLog { get; set; }
}
}

Controller:

public class DeviceMapController : Controller
{
    [ActionName("Index")]
    public async Task<ActionResult> Map1Async()
    {
        string empty = "Unknown";

        var items = await DocumentDBRepository<DeviceMap>.GetMap1Async(d => d.Id != null, d => d.Lat != empty);
        if (Convert.ToInt32(User.GroupId()) != 200) 
            {
                items = items.Where(d => d.GroupId == Convert.ToInt32(User.GroupId()));

        }

        return View(items);

    }
}

View:

             @foreach (var item in Model)
                    {


                        if ((@item.IPaddress == "192.168.2.14") || (@item.IPaddress == "192.168.2.13") || (@item.IPaddress == "192.168.2.15") || (@item.IPaddress == "192.168.2.16")) { }
                        else
                        {

                            //SideId string
                            string siteId = null;
                            string newsiteId = null;
                            if (item.IPaddress != "0")
                            {

                                int index = item.IPaddress.IndexOf('.') + 1;
                                int space = item.IPaddress.IndexOf('.', index + 1);
                                int space2 = item.IPaddress.IndexOf('.', space + 1);
                                int end = item.IPaddress.Length;
                                if (index > 0) { siteId = item.IPaddress.Substring(space + 1, end - space - 1); newsiteId = siteId.Replace('.', '-'); }
                            }
                           //  string Cutoff =Html.DisplayFor(modelItem => item.LastContact.Ping).ToString();
                         // DateTime day = DateTime.Parse(Cutoff.Value,"dd/MM/yyyy HH:mm:ss", CultureInfo.CurrentCulture);

                          DateTime myday =Html.DisplayFor(modelItem => item.LastContact.Ping);
                            DateTime now = DateTime.Now;
                            DateTime yesterday = now.AddDays(-7);
                            DateTime d;
                       //  DateTime.TryParseExact(myday,@"dd/MM/yyyy HH:mm:ss", CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal,out d);


                          // if (Html.DisplayFor(modelItem => item.LastContact.Ping) != null) { d = DateTime.Parse(myday, "dd/MM/yyyy HH:mm:ss", CultureInfo.CurrentCulture); } else { myday = DateTime.ParseExact("08/04/2000 14:00:02", "dd/MM/yyyy HH: mm:ss", CultureInfo.CurrentCulture); }

                            string a = @item.Name;



                            <tr>

                                <td>

                                    @if (a.Length > 50) { a = a.Substring(0, 50); }



                                        @if (item.GroupId != 82)
                                        {

                                            if (myday <= DateTime.Now.AddDays(-7))
                                            {<h4>@myday</h4>
                                                    <img src="/Content/Images/trafficlight-red2.png" width="20" height="20"><a href="@Url.Action("DevicePage", "Device", new { item.DeviceId })"><h6>@a..</h6></a>
                                            }
                                            else
                                            {<img src="/Content/Images/trafficlight-green1.png" width="20" height="20"><a href="@Url.Action("DevicePage", "Device", new { item.DeviceId })"><h6>@a..</h6></a>
                                            }
                                        }


                                        else
                                        {


                                            if (myday <= DateTime.Now.AddDays(-7))
                                            {
                                                <img src="/Content/Images/trafficlight-red2.png" width="20" height="20"><a href="@Url.Action("Form", "TARP", new { item.DeviceId })"><h6>@a..</h6></a>
                                            }
                                            else
                                            {<img src="/Content/Images/trafficlight-green1.png" width="20" height="20"><a href="@Url.Action("Form", "TARP", new { item.DeviceId })"><h6>@a..</h6></a>

                                            }

                                        }

                                        @if (item.IPaddress != "0")
                                        {<p>Site Id: @newsiteId;</p>}
                                    @if (item.LastPing != null)
                                    {
                                        <p>
                                            Last Contact: @Html.DisplayFor(modelItem => item.LastContact.Ping), @Html.DisplayFor(modelItem => item.BatVoltage)V

                                        </p>}


I want to disply Ping date and time. Please, help. Also if you have resources on how to call different styled JSON data please provide link for reference. Thank you.

1

There are 1 best solutions below

9
Jawad On BEST ANSWER
public class DeviceMap
{
    [JsonProperty(PropertyName = "id")]
    public string Id { get; set; } // Suggestion: Change this to 'Guid' instead of string

    [JsonProperty(PropertyName = "IPaddress")]
    public string IPaddress { get; set; }

    [JsonProperty(PropertyName = "SpeedLog")]
    public bool SpeedLog { get; set; }

    [JsonProperty(PropertyName = "LastContact")]
    public Entry LastContact { get; set; }
}

public class Entry

{
    [JsonProperty(PropertyName = "EnvLog")]
    public DateTime EnvLogtime { get; set; }

    [JsonProperty(PropertyName = "Ping")]
    public DateTime Ping { get; set; }

    [JsonProperty(PropertyName = "SpdLog")]
    public DateTime SpdLog { get; set; }
}

Your LastContact will deserialize correctly if you select DateTime as the type of each variable in Entry.

Testing

I used your json and converted it to DeviceMap object to test it and make sure that above works.

{
  "DataTypeId": 1,
  "IPaddress": "192.168.2.177",
  "id": "d1b81653-b7a5-4d79-85ea-79c01f43f747",
  "PhoneNo": "0417518324",
  "LastContact": {
    "EnvLog": "2019-09-07T19:41:08",
    "Ping": "2020-01-09T12:10:09",
    "SpdLog": "2019-09-07T19:41:08"
  },
  "SpeedLog": true,
  "DeviceModelId": 2,
  "DisconnectEvents": 9
}

and used the following in my main to deserialize it to make sure it works correctly.

DeviceMap map = JsonConvert.DeserializeObject<DeviceMap>(json);

Screenshot of Data in map.

It is definitely better to define the types in class so that at time of deserialization, you wont have to parse it to the types they should be. Deserializer should take care of that for you and convert your strings to type of your class if it is convertible, like, automatically converting string to Guid or DateTime.