2012-04-02 4 views
4

다음과 같은 모델, 뷰 및 컨트롤러가 있습니다.MVC 3 - JSON 시리얼 라이저

모델

public class Person { 
     public string Name;// { get; set; } 
     public string Occupation { get; set; } 
     public int Salary { get; set; } 
     public int[] NumArr { get; set; } 
    } 

보기

<input type="button" id="Test" value="Test" /> 

@section Javascript{ 
<script type="text/javascript"> 
    $(function() { 
     $("#Test").click(function() { 
      var data = { Name: "Michael Tom", Occupation: "Programmer", Salary: 8500, NumArr: [2,6,4,9] }; 
      var url = "Home/GetJson"; 
      $.ajax({ 
       url: url,     
       dataType: "json", 
       type: "POST", 
       data: data, 
       traditional: true, 
       success: function (result) { 

       } 
      }); 

     }); 
    });   
</script> 
} 

컨트롤러

위의 그 코드를 기반으로
public class HomeController : Controller 
    { 
     public ActionResult Index() 
     { 
      return View(); 
     } 

     public JsonResult GetJson(Person person) {    

      return Json(......); 
     } 
    } 

, I 세 가지 질문을하고 싶습니다.

  1. 우리가 대신 속성의 공공 필드를 사용하는 경우, 시리얼 라이저는 C#을 모델로 JSON 개체 그래서 난 항상 컨트롤러의 "이름"필드에 null을 얻을 직렬화하지 않습니다. 왜 그렇게 된거야?

  2. NumArr 속성 유형을 List로 변경하면 작동하지 않습니다. int [] 대신 List를 어떻게 사용할 수 있습니까? 내가 JS에서 배열을 전달하는 거 알아. JS에서 List를 전달할 수 있습니까?

  3. serialization이 "traditional : false"로 작동하지 않기 때문에 View의 Javascript 코드 블록에서 "traditional : true"를 사용하고 있습니다. jQuery에는 세 가지 버전의 Json serializer가 있다고 들었습니다. ASP.NET MVC의 serializer는 이전 버전 만 지원합니다. 사실입니까?

3.1. 사실이라면 jQuery의 최신 버전을 지원하는 MVC의 시리얼 라이저의 최신 버전을 언제 얻을 것인지 알고 싶습니다.

3.2. 사용자 정의 뷰 엔진을 등록 할 수있는 것처럼 사용자 정의 Javascript Serializer를 등록 할 수있는 방법이 있습니까? 내 친구는 저에게 사용자 정의 값 공급자 또는 사용자 정의 모델 바인더를 등록하고 사용자 정의 값 공급자/모델 바인더에서 사용자 정의 JS 직렬기를 사용할 수 있다고 제안했습니다.

미리 감사드립니다. 제 질문에 대해 명확하지 않으면 알려주십시오. 감사!

답변

14

1) 우리는 대신 속성의 공공 필드를 사용하는 경우, 직렬 그래서 나는 항상 컨트롤러 "이름"필드에 null를 얻을 C#을 모델로 JSON 객체를 직렬화하지 않습니다. 왜 그렇게 된거야?

모델 바인더는 속성과 함께 작동하기 때문에. 의도적으로 설계된 것입니다. 일반적으로 필드는 클래스에서 비공개이어야합니다. 구현 세부 사항입니다. 속성을 사용하여 외부 세계에 일부 동작을 노출합니다.

2) NumArr 속성의 유형을 List로 변경 한 경우 이 작동하지 않습니다. int [] 대신 List를 어떻게 사용할 수 있습니까? JS에서 배열 을 전달하는 것을 알고 있습니다. JS에서 List를 전달할 수 있습니까?

그래야합니다. List<int>, IEnumerable<int> 또는 int[]과 상관없이 모두 동일하며 작동합니다.당신이 예를 들어 List<SomeComplexType>과 같은 복잡한 객체의 집합을 사용하고 싶다면 어떻게 될까요? (이 문제에 대한 해결책은 아래를보십시오).

3) 나는 "전통 : true"로 사용하고 직렬화가 "거짓 전통적인"작동하지 않기 때문에보기의 자바 스크립트 코드 블록이다. 나는 jQuery에는 Json 시리얼 라이저의 세 가지 버전이 있다고 들었습니다. ASP.NET MVC의 serializer 은 이전 버전 만 지원합니다. 사실입니까?

예, traditional parameter은 jQuery가 매개 변수를 serialize하는 방식을 변경했을 때 jQuery 1.4에 도입되었습니다. 변경 내용은 모델 바인더가 MVC에서 사용하는 표준 규칙 인 binding to lists과 호환되지 않는 것으로 나타났습니다.

그래서 FireBug와 같은 자바 스크립트 디버깅 도구를 다운로드하고 재생을 시작하십시오. 이 매개 변수를 설정할 때 jQuery가 요청을 보내는 방식에 차이가 있음을 알 수 있습니다.


JSON 인코딩 된 요청을 컨트롤러 동작에 전송하는 것이 좋습니다. 이것은 모든 복잡한 객체에서 작동하며 JSON이 표준 상호 운용 형식이기 때문에 어떤 버전의 jQuery를 사용하고 있는지 물어볼 필요가 없습니다. 표준 상호 운용 형식의 장점은 어떤 시스템을 사용하든 관계없이 동일한 언어로 말할 수 있어야한다는 것입니다 (물론 시스템에 버그가 있으며 정의 된 표준을 따르지 않는 한).

하지만 지금은 application/x-www-form-urlencoded도 표준이며 inetroperable 형식이라고 말할 수 있습니다. 그리고 그것은 사실입니다. 문제는 모델 바인더가 입력 필드의 이름을 모델의 속성으로 바인딩 할 때 규칙을 사용한다는 것입니다. 그리고이 협약은 상호 운용성 또는 산업 표준과는 거리가 멀습니다.

public class Person 
{ 
    public string Name { get; set; } 
    public string Occupation { get; set; } 
    public int Salary { get; set; } 
    public List<SubObject> SubObjects { get; set; } 
} 

public class SubObject 
{ 
    public int Id { get; set; } 
    public string Name { get; set; } 
} 

당신은 (JSON 형식에서 지원되지 않는 순환 참조의 예외에) 당신이 좋아하는 복잡한 계층 구조를 상상할 수 :

그래서 예를 들어, 당신은 모델의 계층 구조를 가질 수있다.

다음 : 우리는 나타 내기 위해 application/json에 Content-Type을 요청 HTTP 헤더를 설정

var data = { 
    name: "Michael Tom", 
    occupation: "Programmer", 
    salary: 8500, 
    subObjects: [ 
     { id: 1, name: 'sub 1' }, 
     { id: 2, name: 'sub 2' }, 
     { id: 3, name: 'sub 3' } 
    ] 
}; 

$.ajax({ 
    url: "Home/GetJson", 
    type: "POST", 
    data: JSON.stringify({ person: data }), 
    contentType: 'application/json', 
    success: function (result) { 

    } 
}); 

내장 요청이 JSON합니다 ( JSON.stringify 방법을 사용하여) 인코딩 된 JSON 값 공급자 공장과는 것이다 강력한 형식의 모델로 다시 구문 분석하십시오. JSON.stringify 방법은 최신 브라우저에 기본적으로 내장되어 있지만 레거시 브라우저를 지원하려면 페이지에 json2.js 스크립트를 포함 할 수 있습니다.

+0

세부 사항을 보내 주셔서 감사합니다. 감사! –

관련 문제