ahs*_*ele 39 asp.net-mvc serialization json circular-reference
我有一个对象,它具有对另一个对象的循环引用.鉴于这些对象之间的关系,这是正确的设计.
为了显示
Machine => Customer => Machine
Run Code Online (Sandbox Code Playgroud)
正如我所料,当我尝试使用Json来序列化机器或客户对象时,我遇到了一个问题.我不确定的是如何解决这个问题,因为我不想打破Machine和Customer对象之间的关系.解决此问题的选项有哪些?
编辑
目前我正在使用Controller基类提供的Json方法.所以我正在做的序列化基本如下:
Json(machineForm);
Run Code Online (Sandbox Code Playgroud)
Aar*_*ght 57
更新:
不要试图使用NonSerializedAttribute,因为JavaScriptSerializer显然忽略了它.
相反,使用ScriptIgnoreAttributein System.Web.Script.Serialization.
public class Machine
{
public string Customer { get; set; }
// Other members
// ...
}
public class Customer
{
[ScriptIgnore]
public Machine Machine { get; set; } // Parent reference?
// Other members
// ...
}
Run Code Online (Sandbox Code Playgroud)
这样,当你折腾Machine到Json方法,它会遍历从关系Machine到Customer但不会尝试去从后Customer到Machine.
这个关系仍然存在,你的代码可以随意使用,但是JavaScriptSerializer(由Json方法使用)将忽略它.
eud*_*mos 33
尽管它的年龄,我回答这个问题,因为它是第三结果(目前)从谷歌"json.encode循环引用",虽然我并不与上面的答案(完全)同意,在使用ScriptIgnoreAttribute假定您代码中的任何地方都不会想要在某个JSON的另一个方向上遍历关系.由于一个用例,我不相信锁定你的模型.
它确实激励我使用这个简单的解决方案.
既然你在MVC视图的工作,你有产品型号和你想简单的控制器内分配模型到ViewData.Model,继续使用您的视图中的LINQ查询扁平化的数据很好地消除违规您想要的特定JSON的循环引用:
var jsonMachines = from m in machineForm
select new { m.X, m.Y, // other Machine properties you desire
Customer = new { m.Customer.Id, m.Customer.Name, // other Customer properties you desire
}};
return Json(jsonMachines);
Run Code Online (Sandbox Code Playgroud)
或者如果机器 - >客户关系是1 ..* - >*然后尝试:
var jsonMachines = from m in machineForm
select new { m.X, m.Y, // other machine properties you desire
Customers = new List<Customer>(
(from c in m.Customers
select new Customer()
{
Id = c.Id,
Name = c.Name,
// Other Customer properties you desire
}).Cast<Customer>())
};
return Json(jsonMachines);
Run Code Online (Sandbox Code Playgroud)
Tho*_*mas 10
基于txl的答案,您必须禁用延迟加载和代理创建,您可以使用常规方法来获取数据.
例:
//Retrieve Items with Json:
public JsonResult Search(string id = "")
{
db.Configuration.LazyLoadingEnabled = false;
db.Configuration.ProxyCreationEnabled = false;
var res = db.Table.Where(a => a.Name.Contains(id)).Take(8);
return Json(res, JsonRequestBehavior.AllowGet);
}
Run Code Online (Sandbox Code Playgroud)