【问题标题】:Creating C# object from JSON data retrieved from HttpWebResponse从从 HttpWebResponse 检索到的 JSON 数据创建 C# 对象
【发布时间】:2015-03-25 23:44:57
【问题描述】:

首先,我绝对不擅长编程。我一直都是。世界上任何其他人似乎只是“得到”的最简单、最微不足道的事情往往会绊倒我并导致我无法控制的愤怒退出。顺便说一句,对不起这个愚蠢的问题。 :P

我基本上是在尝试获取一些从 HttpWebResponse 返回的 JSON 值并将它们放入 C# 对象中。 JSON 值与客户端列表有关。我希望能够将它们转换为 C# 对象,然后我可以在整个程序中使用这些对象(例如 client.name、client.phone_number 等...)。

下面的代码更像是概念证明而不是最终代码。我登录到一个 WordPress 站点,然后从站点上的一个页面中提取 JSON 数据。我能够检索并查看返回的 JSON 数据(作为一个长而混乱的字符串)。我只是不知道如何从该字符串中提取我需要从中创建“客户端”对象的特定值。

        string loginUri = "URL TO WORDPRESS LOGIN";
        string username = entryUsername;
        string password = entryPassword;
        string reqString = "log=" + username + "&pwd=" + password;
        byte[] requestData = Encoding.UTF8.GetBytes(reqString);

        CookieContainer loginCookie = new CookieContainer();
        var request = (HttpWebRequest)WebRequest.Create(loginUri);
        request.Proxy = null;
        request.AllowAutoRedirect = false;
        request.CookieContainer = loginCookie;
        request.Method = "POST";

        request.ContentType = "application/x-www-form-urlencoded";
        request.ContentLength = requestData.Length;
        using (Stream s = request.GetRequestStream())
        {
            s.Write(requestData, 0, requestData.Length);

            using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
            {
                foreach (Cookie currentCookie in response.Cookies)
                {
                    Console.WriteLine(currentCookie.Name + " = " + currentCookie.Value); // debug purposes
                    request.CookieContainer.Add(currentCookie);
                }
            }
        }

        // Debug purposes
        Console.WriteLine("{0} cookie(s) have been downloaded, Jim.", loginCookie.Count.ToString());

        string clientListURI = "PAGE CONTAINING JSON";
        HttpWebRequest clientListRequest = (HttpWebRequest)WebRequest.Create(clientListURI);
        clientListRequest.Proxy = null;
        clientListRequest.Method = "POST";
        clientListRequest.ContentLength = 0;
        clientListRequest.ContentType = "application/json";
        clientListRequest.CookieContainer = loginCookie;
        using (HttpWebResponse clientListResponse = (HttpWebResponse)clientListRequest.GetResponse())
        using (Stream resSteam = clientListResponse.GetResponseStream())
        {
            JsonValue jsonDoc = JsonObject.Load(resSteam);
            Console.WriteLine("Response: {0}", jsonDoc.ToString ());
        }          

示例 Json:

{
    id: "26",
    owner: "7",
    owner_name: "Bradford Kolumbic",
    Status: "0",
    status_name: "None",
    Milestone: "0",
    milestone_name: "None",
    small_text_1: "Ghost Buster Solutions",
    small_text_8: "Business",
    small_text_7: "(858) 123-5432",
    small_text_2: "123 ABC Street",
    small_text_4: "Escondido",
    small_text_5: "California",
    small_text_6: "92027"
}

我创建了一个类 Client,可用于存储返回的 JSON 中的每个客户端配置文件。

public class Client
{
    public string id { get; set; }
    public string owner { get; set; }
    public string owner_name { get; set; }
    public string Status { get; set; }
    public string status_name { get; set; }
    public string Milestone { get; set; }
    public string milestone_name { get; set; }
    public string small_text_1 { get; set; }
    public string small_text_8 { get; set; }
    public string small_text_7 { get; set; }
    public string small_text_2 { get; set; }
    public string small_text_4 { get; set; }
    public string small_text_5 { get; set; }
    public string small_text_6 { get; set; }
}

我尝试了各种不同的方法,但似乎没有什么适合我。我确定我遗漏了一些非常明显的东西。

我尝试的最后一件事是:

var JsonClientList = JsonConvert.DeserializeObject<List<Client>>(jsonDoc); 

虽然“无法将 'System.Json.JsonObject' 类型的对象转换为 'System.Json.JsonPrimitive' 类型,但它会出错。”

对这位年轻的傻瓜的任何帮助将不胜感激。感谢您的宝贵时间。

【问题讨论】:

  • 检查网站json2csharp.com 将您的 json 粘贴到其中,您将获得所需的课程
  • 您能否发布一个您尝试转换的 JSON 示例?
  • @MichalCiechan,确定!以下是来自其中一位客户的示例数据:{ id:“26”,所有者:“7”,所有者名称:“Bradford Kolumbic”,状态:“0”,状态名称:“无”,里程碑:“0”,里程碑名称:“无”,small_text_1:“Ghost Buster 解决方案”,small_text_8:“商业”,small_text_7:“(858) 123-5432”,small_text_2:“ABC 街 123 号”,small_text_4:“Escondido”,small_text_5:“加利福尼亚”,small_text_6: "92027" },
  • 您的结果是真正的 JSON 格式,在 JSON 中属性名称使用“”进行转义。例如。 "id":"26"
  • @MichalCiechan 我很抱歉我误解了你,我以为你是在从网站上找一个例子。我收到的实际结果实际上是这样的:“Bradford Kolumbic”、“small_text_8”:“Business”、“small_text_7”:“(858) 123-5432”,-等等...

标签: c# json xamarin


【解决方案1】:

这对我有用

var json =@"
{
    id: ""26"",
    owner: ""7"",
    owner_name: ""Bradford Kolumbic"",
    Status: ""0"",
    status_name: ""None"",
    Milestone: ""0"",
    milestone_name: ""None"",
    small_text_1: ""Ghost Buster Solutions"",
    small_text_8: ""Business"",
    small_text_7: ""(858) 123-5432"",
    small_text_2: ""123 ABC Street"",
    small_text_4: ""Escondido"",
    small_text_5: ""California"",
    small_text_6: ""92027""
}";

var c = JsonConvert.DeserializeObject<Client>(json); 

如果您提供的示例是整个 JSON 对象,那么它不是客户端集合 (List&lt;Client&gt;),而只是一个 Client

【讨论】:

  • 那只是我展示的一个客户(我不得不编辑一些细节)。我无法复制/粘贴整个 JSON 数据(价值超过 40 个客户端),因为它包含敏感信息。我尝试这样做的原因是我们有一个可以在 CRM 上在线查看的客户列表。我正在尝试构建网站 CRM 的移动应用程序版本,该版本将有一个部分,用户可以在其中显示他们的客户列表,就像他们可以在线一样。它将从 Web 响应中提取信息,然后我可以将该数据动态填充到客户端列表中。
  • 您可以发布 2 个客户(伪造信息),但需要查看主 json 文件的结构,而不仅仅是其中的一部分。父数组的设置方式有问题
  • 它甚至可以是相同的客户端,你发布的只需要主数组的结构(不是里面的ifno)
  • 当然,这里有一个更好的示例。它只包含两个客户端,但保留了所有其余的 JSON 代码。 development.bradfordkolumbic.com/json_sample.html
  • 刚刚注意到owner_name:“John Doe“。这些与 JSON 期望的双引号字符不同
【解决方案2】:

我建议你去这里:http://json2csharp.com/ 并输入你的 JSON。他们会立即为您创建 C# 类。

然后我会将 NewtonSoft.Json nuget-package 添加到我的项目中。然后最后调用类似的东西

JsonConvert.Deserialize<List<Client>>(jsonDoc);

【讨论】:

  • 我之前尝试过,但一直收到以下错误:无法将“System.Json.Object”类型的对象转换为“System.Json.JsonPrimitive”类型
【解决方案3】:

这是我正在使用的代码。 执行 HTTPRequest:

 public static string DoJsonRequest(string url, MemoryStream content)
        {

            byte[] dataByte = content.ToArray();

            //create http web request obj
            WebRequest postRequest = WebRequest.Create(url);
            //Method type
            postRequest.Method = "POST";
            // Data type - message body coming in xml
            postRequest.ContentType = "application/json; charset=utf-8";
            //Content length of message body
            postRequest.ContentLength = dataByte.Length;

            // Get the request stream
            using (Stream postStream = postRequest.GetRequestStream())
            {
                // Write the data bytes in the request stream
                postStream.Write(dataByte, 0, dataByte.Length);
                //Get response from server
                using (HttpWebResponse postResponse = (HttpWebResponse)postRequest.GetResponse())
                {
                    using (StreamReader reader = new StreamReader(postResponse.GetResponseStream()))
                    {
                        return reader.ReadToEnd();
                    }
                }
            }
        }



        public static string GetJsonFromObject<TObject>(TObject obj, IEnumerable<Type> types)
        {
            using (var stream = new MemoryStream())
            {
                var jsSerializer = new DataContractJsonSerializer(typeof(TObject), types);

                jsSerializer.WriteObject(stream, obj);
                stream.Position = 0;

                using (StreamReader reader = new StreamReader(stream))
                {
                    string json = reader.ReadToEnd();
                    return json;
                }
            }
        }



public static TObject GetObjectFromJson<TObject>(string json, IEnumerable<Type> types)
{

    using (MemoryStream stream = new MemoryStream())
    {
        using (StreamWriter writer = new StreamWriter(stream))
        {
            writer.Write(json);
            writer.Flush();
            stream.Position = 0;

            var jsSerializer = new DataContractJsonSerializer(typeof(TObject), types);

            TObject obj = (TObject)jsSerializer.ReadObject(stream);

            return obj;
        }
    }
}

你可以看到我正在使用泛型。

用于调用方法并向 RESTFull 服务发出请求。

 using (MemoryStream stream = new MemoryStream())
                {
                    using (StreamWriter writer = new StreamWriter(stream))
                    {
                        writer.Write(json);
                        writer.Flush();
                        stream.Position = 0;

                        string response = HttpHelper.DoJsonRequest("https://localhost:44300/RestFull.svc/Execute", stream);

                        response = response.Remove(0, 1);
                        response = response.Remove(response.Length - 1, 1);
                        response = response.Replace("\\\"", "\"");
                        Data data = HttpHelper.GetObjectFromJson<Data>(response, Types);

                    }
                }

其中 Json = "\"" + HttpHelper.GetJsonFromObject&lt;Data&gt;(request, Types).Replace("\"", "\\\"") + "\"";

【讨论】:

    【解决方案4】:

    哦,如果您使用的是 Vs 2013,另一种方法是在剪贴板上获取 JSON。在 VS 中创建一个新文件,然后选择性粘贴。噗,一切准备就绪。

    标记

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-02-18
      • 2020-07-10
      • 2021-12-30
      • 1970-01-01
      • 1970-01-01
      • 2016-09-28
      • 2018-08-06
      • 1970-01-01
      相关资源
      最近更新 更多