2017-10-19 2 views
0

다른 서비스를 호출하고 응답 배열을 반환하는 웹 API를 만들려고합니다. 호출 된 서비스가 응답을 반환합니다. 나는 부름받은 서비스에서 개별 항목을 얻을 수있다. 그러나 항목의 배열을 만들고 API에서 응답으로 반환하는 방법을 모르겠다. json으로는 서비스에서 반환Web API에서 응답 배열 반환 C#

{ 
"cr_response": { 
    "details": [{ 
     "name": "Req", 
     "fields": [{ 
       "value": "Prj0\r\nPrj1", 
       "name": "Project" 
      }, 
      { 
       "value": "October 13, 2017 14:18", 
       "name": "Submitted" 
      }, 
      { 
       "value": "John", 
       "name": "Rec Name" 
      } 
     ] 
    }], 
    "cr_metadata": {} 
} 
} 

처럼 보이는 아래

public class Field 
{ 
    public string value { get; set; } 
    public string name { get; set; } 
} 

public class Detail 
{ 
    public string name { get; set; } 
    public List<Field> fields { get; set; } 
} 

public class CrMetadata 
{ 
} 

public class CrResponse 
{ 
    public List<Detail> details { get; set; } 
    public CrMetadata cr_metadata { get; set; } 
} 

public class RootObject 
{ 
     public CrResponse cr_response { get; set; } 
} 

이 서비스의 응답을 서비스를 호출하고 검색하기위한 코드가 같은 POCO 클래스는 보이는

var response = await iLab_client.GetAsync(uri); 
var datafile = await response.Content.ReadAsStringAsync(); 
var returnDataObj = JsonConvert.DeserializeObject<DTO.RootObject>(datafile); 

foreach (var form in returnDataObj.cr_response.details) 
{ 
    name_response = form.name; 
    return Ok(name_response); 
} 

여기에서 세부 정보에서 이름에 액세스 할 수 있지만 확실하지는 않습니다. 필드의 모든 이름과 값에 액세스하여 배열로 구성 할 수 있습니까? JSON 응답으로 보내주십시오. 나는

  foreach (var form in returnDataObj.cr_response.details) 
      { 
       var id_response = form.fields; 
       return Ok(id_response); 
      } 

같은 시도하지만

+0

나는 오류 메시지가 특정 콘텐츠 유형'응용 프로그램/xml'을 언급 것을 알 수 있습니다. 유효한 XML은 하나의 루트 노드가 있어야합니다. 반환 된 객체가 컬렉션이 될 수없는 가능성이 있습니다. 클라이언트를 변경하여 JSON을 요청하면 문제가 해결 될 수 있습니다. 그렇지 않으면 배열을 직접 반환하는 대신 배열을 가진 객체를 속성 중 하나로 반환하는 것이 좋습니다. – StriplingWarrior

+0

@StriplingWarrior HttpClient 대신 변경 하시겠습니까? – xyz

+0

아니요. 귀하의 코드는 * 웹 서비스 ('ilab_client.GetAsync (...)')와 * 클라이언트 ('return Ok (...);')에 의해 소비되고 있습니다. 웹 API 엔드 포인트를 사용하는 클라이언트가 HTTP 요청을 전송 중입니다. 웹 API는 요청을보고 JSON이 아닌 XML로 응답을 직렬화해야한다고 생각합니다. 이는 웹 요청에서 헤더 (또는 헤더 부재)가 원인 일 수 있습니다. 또는 [웹 API 응용 프로그램이 구성된 방식] 때문일 수 있습니다 (https://stackoverflow.com/q/12629144/120955). 또는이 두 가지 조합. – StriplingWarrior

답변

0

당신이 당신의 배열을 작성 foreach 루프 외부를 반환해야 웹 API에서 배열을 반환하려면 오류 System.InvalidOperationException

<Error> 
<Message>An error has occurred.</Message> 
<ExceptionMessage> 
The 'ObjectContent`1' type failed to serialize the response body for content 
type 'application/xml; charset=utf-8'. 
</ExceptionMessage> 

처럼 던져 :

var list = new List<string>(); 
foreach (...){ 
    var name = ... 
    list.Add(name); 
} 
return Ok(list.ToArray()); // or just return Ok(list); 

이것은 ho입니다. POCO-JSON를 역 직렬화 및 이름의 목록을 얻을 W :

[TestMethod] 
public void TestJsonToPocoAndGetNames() 
{ 
    const string Json = @" 
     { 
     ""cr_response"": { 
      ""details"": [{ 
       ""name"": ""Req"", 
       ""fields"": [{ 
         ""value"": ""Prj0\r\nPrj1"", 
         ""name"": ""Project"" 
        }, 
        { 
         ""value"": ""October 13, 2017 14:18"", 
         ""name"": ""Submitted"" 
        }, 
        { 
         ""value"": ""John"", 
         ""name"": ""Rec Name"" 
        } 
       ] 
      }], 
      ""cr_metadata"": {} 
     } 
    } 
    "; 

    var settings = new JsonSerializerSettings 
    { 
     MetadataPropertyHandling = MetadataPropertyHandling.Ignore, 
     DateParseHandling = DateParseHandling.None, 
    }; 
    var response = JsonConvert.DeserializeObject<RootJsonObject>(Json, settings); 

    var names = new List<string>(); 
    foreach (var detail in response.CrResponse.Details) 
    { 
     names.Add(detail.Name); 

     foreach (var field in detail.Fields) 
     { 
      names.Add(field.Name); 
     } 
    } 

    Assert.AreEqual(
     "Req, Project, Submitted, Rec Name", 
     string.Join(", ", names.ToArray())); 
} 

POCO 클래스 :

public class RootJsonObject 
{ 
    [JsonProperty("cr_response")] 
    public CrResponse CrResponse { get; set; } 
} 

public class CrResponse 
{ 
    [JsonProperty("cr_metadata")] 
    public CrMetadata CrMetadata { get; set; } 

    [JsonProperty("details")] 
    public Detail[] Details { get; set; } 
} 

public class CrMetadata 
{ 
} 

public class Detail 
{ 
    [JsonProperty("fields")] 
    public Field[] Fields { get; set; } 

    [JsonProperty("name")] 
    public string Name { get; set; } 
} 

public class Field 
{ 
    [JsonProperty("name")] 
    public string Name { get; set; } 

    [JsonProperty("value")] 
    public string Value { get; set; } 
} 
+0

우리는 필드뿐만 아니라 세부 사항에 이름을 가지고 있습니다. 나는 필드에서 이름과 가치를 얻고 싶습니다. – xyz

+0

JSON 데이터에 POCO 클래스로 deserialize하지 않고 액세스하려면 https://stackoverflow.com/questions/6620165/how-can-i-parse-json-with-c/17842600#17842600 –

+0

을 사용하는 것이 좋습니다. POCO는 내가 파일과 이름 아래서 접근 할 수 없습니까? – xyz