Angular js post无法序列化对象

Posted

技术标签:

【中文标题】Angular js post无法序列化对象【英文标题】:Angular js post cannot serialize object 【发布时间】:2021-09-30 18:47:02 【问题描述】:

目前我正在向我的控制器发送 AngularJS Post,而不是提交表单。我有一个名为sharingInfo 的对象,在调用后始终在控制器中设置为null。我认为 JSON 序列化程序存在问题。

在 Angular 中我像这样发布数据

$scope["TemplateForm"].$setPristine();
                    var model = getFormData($('#TemplateForm'));

                    model.Publish = publish;
                    model["Template.CommitteeWithAccessCanEditReusable"] = $scope.Model.Template.CommitteeWithAccessCanEditReusable;
                    model["Template.SharingInfo"]  = angular.toJson($scope.Model.Template.SharingInfo);
                    $http(
                        method: "POST",
                        url: "/Template/UpdateTemplateContent",
                        data: model
                    ).then...morecode=>

在调试器中,template.sharingInfo 被序列化为

""CommitteesWithAccess":["TenantId":32727,"DisplayName":"20190304 Ted Test Committee","IsStatic":false,"RootCommitteeId":null]"""CommitteesWithAccess":["TenantId":32727,"DisplayName":"20190304 Ted Test Committee","IsStatic":false,"RootCommitteeId":null]"

当数据到达控制器时,调试器总是将值设置为 null。此外,对于字符串或布尔类型的对象,我可以设置值。我相信它只是没有序列化到对象中,所以我决定序列化 sharedInfo 以查看它的期望。我通过添加一个字符串类型的虚拟sharingInfo 变量来做到这一点。此变量保留 json 字符串,然后在控制器中对其进行反序列化。此解决方法不可维护,因为它迫使我定义两个同名但类型不同的变量,并且我无法更改sharingInfo 对象。

我的控制器方法定义如下:templatedto.sharingInfo 是一个字符串,templatedto.template.sharinginfo 是对象

[AcceptVerbs(HttpVerbs.Post)]
        [RequireReusablesPermissions]
        public ActionResult UpdateTemplateContent(SaveTemplateDto templateDto)
        

            if (templateDto.SharingInfo != null && templateDto.Template.SharingInfo != null)
            
                templateDto.Template.SharingInfo = JsonConvert.DeserializeObject<ReusableDto.SharingState>(templateDto.SharingInfo) as ReusableDto.SharingState;
            
            //just to see what this gives me tbd
            var serializedObject = JsonConvert.SerializeObject(templateDto.Template.SharingInfo);

            var validationResults = TemplateValidator.GetValidationErrors(templateDto);

            if (validationResults?.Any() == true)
            
                return new AjaxResult<ReusableDto>
                
                    ResponseResultCode = ResponseResultCode.Failure,
                    MessagesHeader = $"Resources.UnableToSaveTemplate string.Join(",", validationResults)"
                ;
            

“serializedObject”返回这个字符串:

"\"CommitteesWithAccess\":[\"TenantId\":32727,\"DisplayName\":\"20190304 Ted Test Committee\",\"IsStatic\":false,\"RootCommitteeId\":null]" 

您可以看到 angular.toJson 和 c# JSON 序列化程序,以不同的方式序列化对象。 我怎样才能让它在 Angular 中进行预期的序列化?

我的对象定义如下供参考。可重用的DTO是模板

     public class SaveTemplateDto
        
            public ReusableDto Template  get; set; 
            public bool IsNewTemplate => Template?.Id == Guid.Empty;

            // Model binding properties 
            public bool Publish  get; set; 
            public string SharingInfo  get; set; 
        

 public class ReusableDto
    
        public SharingState SharingInfo  get; set; 

        public class TenantDto
        
            public short TenantId  get; set; 
            public string DisplayName  get; set; 
            public bool IsStatic  get; set; 
            public string RootCommitteeId  get; set; 
        

        public class SharingState 
        
            public List<TenantDto> CommitteesWithAccess  get; set; 
            public List<TenantDto> CommitteesWithoutAccess  get; set;             
        

【问题讨论】:

【参考方案1】:

也许创建一个包装对象

public class CommitteesWithAccessModel

    public SaveTemplateDto  SaveTemplateDto  get; set;


[AcceptVerbs(HttpVerbs.Post)]
[RequireReusablesPermissions]
public ActionResult UpdateTemplateContent(CommitteesWithAccessModel templateDto)

...

【讨论】:

以上是关于Angular js post无法序列化对象的主要内容,如果未能解决你的问题,请参考以下文章

js中常用方法集合

将多个对象从Angular控制器POST到Web API 2

WebAPI 2不反序列化List POST请求中FromBody对象的属性

django REST framework 嵌套序列化器和 POST 嵌套 JSON 文件

无法将 JSON 字符串反序列化为 C# 对象

使用 RestKit 序列化带有子对象的对象 [POSTing]