简体   繁体   English

在Azure APIM中使用JSON.NET反序列化时如何显示十进制值?

[英]How to show the decimal value as it is when Deserializing using JSON.NET in Azure APIM?

I'm using Azure APIM policy expression to aggregate multiple responses.我正在使用 Azure APIM 策略表达式来聚合多个响应。 I have some decimal values in the response.我在响应中有一些小数值。 But while Deserializing, formatting was changed as shown in the output. I want to return as in the Input.但是在反序列化时,格式已更改,如 output 所示。我想返回输入中的格式。

INPUT输入

{
    "x1": 1.55391E4,
    "x2": 2.2173244E5,
    "x3": 1.11226E3,
    "UpdatedDateTime": "2023-01-17T20:45:51.959+08:00"
}

OUTPUT OUTPUT

{
    "x1": 15539.1,
    "x2": 221732.44,
    "x3": 1112.26,
    "UpdatedDateTime": "2023-01-17T20:45:51.959+08:00"
}

EXPECTED预期的

{
    "x1": 1.55391E4,
    "x2": 2.2173244E5,
    "x3": 1.11226E3,
    "UpdatedDateTime": "2023-01-17T20:45:51.959+08:00"
}

This is my fiddle这是我的小提琴

In this sample, I have preserved the DateTimeZone with Offset.在此示例中,我保留了带偏移量的 DateTimeZone。 but I can't do the decimal fields (x1, x2, x3).但我不能做小数字段(x1、x2、x3)。 I just wants to return as it is like input.我只想返回,因为它就像输入一样。

Please note that I'm writing this inside a policy expression, so I can't create any C# extensions or helper methods.请注意,我在策略表达式中编写此内容,因此我无法创建任何 C# 扩展或辅助方法。

One way to force scientific notation for decimal values in a JToken hierarchy would be to replace decimal-valued JValue tokens with an appropriately formatted JRaw value:JToken层次结构中对decimal值强制使用科学记数法的一种方法是用适当格式化的JRaw值替换十进制值的JValue标记:

var settings = new JsonSerializerSettings 
{
    // Make sure that FloatParseHandling is consistent with the later check ".Where(v => v.Value is decimal)"
    FloatParseHandling = FloatParseHandling.Decimal, 
    FloatFormatHandling = FloatFormatHandling.DefaultValue, 
    // Instead of DateParseHandling.DateTimeOffset, you could use DateParseHandling.None to skip DateTime recognition and leave date/time strings unchanged.
    DateParseHandling = DateParseHandling.DateTimeOffset, 
    DateTimeZoneHandling = DateTimeZoneHandling.Unspecified
};

var obj = JsonConvert.DeserializeObject<JObject>(json, settings);

var decimalValues = obj.Descendants().OfType<JValue>().Where(v => v.Value is decimal).ToList(); 
foreach (var value in decimalValues)
{
    value.Replace(new JRaw(((decimal)value.Value).ToString("0.00000E0" /*, System.Globalization.CultureInfo.InvariantCulture */))); // Is System.Globalization.CultureInfo.InvariantCulture available?
}

var newJson = obj.ToString(Formatting.Indented);

Which results in结果是

{
  "x1": 1.55391E4,
  "x2": 2.21732E5,
  "x3": 1.11226E3,
  "UpdatedDateTime": "2023-01-17T20:45:51.959+08:00"
}

Demo fiddle #1 here .演示小提琴 #1在这里

Notes:笔记:

  • You code is inside an Azure APIM policy expression.您的代码位于 Azure APIM 策略表达式中。 Only a very limited set of types are allowed in such an expression, as documented in .NET Framework types allowed in policy expressions .此类表达式中只允许使用非常有限的类型集,如.NET Framework types allowed in policy expressions中所述。 Of note, the following are not available :请注意,以下内容不可用

    • Newtonsoft.Json.JsonConverter . Newtonsoft.Json.JsonConverter
    • Newtonsoft.Json.JsonTextReader and JsonTextWriter . Newtonsoft.Json.JsonTextReaderJsonTextWriter
    • System.Text.Json (all). System.Text.Json (全部)。

    The lack of any ability to create a custom converter is why I suggested to use JRaw .缺乏创建自定义转换器的能力是我建议使用JRaw的原因。

  • You can't preserve the original decimal formatting with Json.NET. When JsonTextReader encounters a floating point JSON number, it parses it to decimal or double and discards the original JSON character sequence .您不能使用 Json.NET 保留原始的十进制格式。当JsonTextReader遇到浮点数 JSON 数字时,它会将其解析为decimaldouble精度并丢弃原始的 JSON 字符序列 Thus only the value (and number of digits in the case of decimal ) is retained.因此,仅保留值(以及decimal情况下的位数)。

  • Utf8JsonReader from System.Text.Json, on the other hand, does retain the underlying JSON character sequence.另一方面,来自 System.Text.Json 的Utf8JsonReader确实保留了底层的 JSON 字符序列。 This character sequence is passed off to JsonElement and JsonNode which also retain the original character sequence and present read-only (or editable) views of it.此字符序列被传递给JsonElementJsonNode ,它们也保留原始字符序列并呈现它的只读(或可编辑)视图。 So if Azure APIM policy expressions are ever enhanced to allow System.Text.Json you would be able to retain the original JSON decimal formatting much more easily.因此,如果 Azure APIM 策略表达式得到增强以允许 System.Text.Json,您将能够更轻松地保留原始的 JSON 十进制格式。

    Demo fiddle #2 here .演示小提琴 #2在这里

  • If you want to leave all date & time string values unchanged, instead of DateParseHandling.DateTimeOffset , you could use DateParseHandling.None to disable DateTime recognition entirely.如果您想保留所有日期和时间字符串值不变,而不是DateParseHandling.DateTimeOffset ,您可以使用DateParseHandling.None完全禁用 DateTime 识别。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何使用 JSON.net 处理同一属性的单个项目和数组 - How to handle both a single item and an array for the same property using JSON.net 如何使用 Azure 管理 APIM 开发人员门户委派 Azure PowerShell - How to manage the Azure APIM developer portal delegation with Azure PowerShell 无法使用 Azure APIM 交互式门户向后端 API 发送测试请求 - Unable to send test requests to backend APIs using the Azure APIM interactive portal 为什么我应该从 APIM 启用 OAuth,因为它已经使用 Microsoft Identity 平台安全 - Why should I enabled OAuth from APIM when it is already secure using Microsoft Identity platform Azure APIM 503 维护响应 - Azure APIM 503 response for maintenance 当小数部分只有 0 时如何在红移中保留小数部分 - how to retain the decimal part in redshift when the decimal part is only having 0 使用消息队列绑定时如何处理Azure Function重跑? - How to handle an Azure Function rerunning when using message queue binding? 如何在 wso2 APIM 4.1 中使用 X-JWT-Assertion header 获取完整的用户声明详细信息? - How to get complete user claims details using X-JWT-Assertion header in wso2 APIM 4.1? 无法使用 WSO2 APIM 在 Stripe 中创建客户 - Unable to create customers in Stripe using WSO2 APIM 如何将 json 文件(json 文件的路径)设置为 Azure 应用程序设置中的值? - How do I set json file(json file's path) to a value in Azure App settings?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM