[英]Is it possible to set Json.Net to ignore $type?
在json反序列化攻击中观看此视频 ,它显示了这一点json,可用于在任何反序列化它的应用程序上触发任意代码执行。
现在在我的应用程序中,我甚至从未使用过类型的json。 我总是反序列化为动态对象或JObject
。 在今天早上另一个无关的对话之前,我甚至都不知道$type
属性。
在我的json设置中是否有一种方法可以告诉它永远不会写或读取此属性? 这不是我想要的东西。
"$type"
信息仅在TypeNameHandling
被修改为TypeNameHandling.None
以外的其他内容时写入 - 这是默认值 。 如果您从未更改过该值,则永远不会发出"$type"
信息。
类似地,当TypeNameHandling = TypeNameHandling.None
(同样是默认值)时,反序列化时会忽略"$type"
属性,如文档中所述:
// for security TypeNameHandling is required when deserializing
Stockholder newStockholder =
JsonConvert.DeserializeObject<Stockholder>(jsonTypeNameAuto, new JsonSerializerSettings
{
TypeNameHandling = TypeNameHandling.Auto
});
如果没有在你的代码(或在代码中使用类库)不断修改TypeNameHandling
比其他东西TypeNameHandling.None
(通过设置或属性, JsonPropertyAttribute.TypeNameHandling
),那么代码执行攻击不能工作。 (有关Json.NET的序列化程序的使用的更准确的细节,这些序列化程序不易受此攻击,请参阅AlvaroMuñoz和Oleksandr Mirosh的黑帽纸 。
另请注意,如果使用JToken.Parse()
(或某些类似的静态方法,如JObject.Parse()
)进行语法分析而不是使用JsonSerializer.Deserialize<T>()
进行反序列化,那么"$type"
属性的存在将只是因为JToken.Parse()
从不调用序列化程序,导致这些属性被填充到JToken
层次结构中。 如果你想在解析后JsonExtensions.RemoveTypeMetadata(this JToken root)
那些"$type"
属性,你可以使用来自用TypeNameHandling.All序列化的Deserialize字符串的 JsonExtensions.RemoveTypeMetadata(this JToken root)
来做到这一点。
话虽这么说,如果一个集合是由另一个使用TypeNameHandling.Arrays
或TypeNameHandling.All
应用程序序列化的,那么JSON中会有一个额外的嵌套级别。 要在反序列化时 IgnoreArrayTypeConverter
它,请参阅Strategies中的 IgnoreCollectionTypeConverter
, 以便在版本/格式之间迁移序列化的Json.NET文档,或者从Make Json.NET中忽略 IgnoreArrayTypeConverter
, 如果它不兼容,则忽略$ type 。
最后,如果您正在使用在属性中设置TypeNameHandling
第三方库,则可以使用自定义合约解析程序禁用它,如在JSON.NET中使用JsonSerializerSettings在属性中指定的如何禁用TypeNameHandling中所示? 。
如果您真的担心团队中的其他人可能启用TypeNameHandling
,您可以创建一个自定义ISerializationBinder
,只要尝试解析类型或类型名称,就会抛出异常:
public class DisallowSerializationBindingBinder : ISerializationBinder
{
#region ISerializationBinder Members
public void BindToName(Type serializedType, out string assemblyName, out string typeName)
{
throw new JsonSerializationException("Binding of subtypes has been disabled");
}
public Type BindToType(string assemblyName, string typeName)
{
throw new JsonSerializationException("Binding of subtypes has been disabled");
}
#endregion
}
然后在JsonSerializerSettings
设置它,如下所示:
var settings = new JsonSerializerSettings
{
SerializationBinder = new DisallowSerializationBindingBinder(),
};
并修改全局设置,如设置默认全局json序列化程序设置 (对于控制台应用程序), 如何在MVC 4 Web API中为Json.NET设置自定义JsonSerializerSettings? (对于ASP.NET Web API)或JsonSerializerSettings和Asp.Net Core (对于asp.net核心)。
不幸的是, TypeNameHandling.None
被忽略。 但你可以使用:
public static JsonSerializerSettings JsonSerializationSettings
= new JsonSerializerSettings
{
MetadataPropertyHandling = MetadataPropertyHandling.Ignore
};
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.