.Net Core 3.0 对象类型设置值

huangapple go评论122阅读模式
英文:

.Net Core 3.0 object Type set value

问题

我正在尝试构建我的.NET Core 3.0 Web API项目,但在最后4天卡住了。以下是我的问题。我有一个名为"GridFilter"的筛选模型,该模型如下:

  1. public class GridFilter
  2. {
  3. public string Operator { get; set; }
  4. public string Field { get; set; }
  5. public object Value { get; set; }
  6. public object Value2 { get; set; }
  7. public string Logic { get; set; }
  8. }

在这个模型中,在过滤任何模型之前,我将Value和Value2保留为对象,然后通过Universal Type Converter将这些值转换为相关的列类型。我在.NET Framework中使用了这个系统,效果非常好。但在.NET Core 3.0中,当我发出请求时,该模型填充如下:

  1. Operator: "eq"
  2. Logic: null
  3. Value: ValueKind = Number : "10000"
  4. Value2: null
  5. Field: "SCT_CATEGORY"

请求:

  1. {"filter": {"filters": [{"field": "SCT_CATEGORY", "value": 10000, "operator": "eq"}]}}

我已经搜索了4天,但无法解决这个问题。我想将其填充为以下形式:

  1. Operator: "eq"
  2. Logic: null
  3. Value: 10000
  4. Value2: null
  5. Field: "SCT_CATEGORY"

我该如何解决这个问题?感谢!

编辑

  1. [Route("[action]")]
  2. [HttpPost]
  3. public async Task<Response> List([FromBody] GridFilter request)

我的ConfigureServices配置如下:

  1. services.AddControllers()
  2. .AddJsonOptions(o =>
  3. {
  4. o.JsonSerializerOptions.PropertyNamingPolicy = null;
  5. o.JsonSerializerOptions.DictionaryKeyPolicy = null;
  6. });

在这个代码片段中,我正在构建用于Fluent NHibernate的筛选器:

  1. internal static MyCriteria BuildFilter(ISession sess, GridFilter gf)
  2. {
  3. MyCriteria mc = null;
  4. var t = !string.IsNullOrEmpty(gf.Field)
  5. ? TypeHelper.GetType(typeof(T).GetProperty(gf.Field))
  6. : null;
  7. if (t == typeof(char) && (!new[] { "eq", "neq" }.Contains(gf.Operator)))
  8. {
  9. gf.Operator = "eq";
  10. }
  11. switch (gf.Operator)
  12. {
  13. case "eq":
  14. mc = gf.Value == null ? new MyCriteria { cr = Restrictions.IsNotNull(gf.Field), logic = gf.Logic.ToEnum(Logic.and) } : new MyCriteria { cr = Restrictions.Eq(gf.Field, ChangeType(gf.Value, t)), logic = gf.Logic.ToEnum(Logic.and) };
  15. break;
  16. // 还有其他操作符的处理...
  17. }
  18. // ...
  19. }

我的ChangeType方法如下:

  1. internal static object ChangeType(object value, Type conversionType)
  2. {
  3. try
  4. {
  5. object result;
  6. UniversalTypeConverter.TryConvert(value, conversionType, out result);
  7. return result;
  8. }
  9. catch (Exception)
  10. {
  11. return false;
  12. }
  13. }

在这一点上,我需要转换的是"10000"而不是ValueKind = Number : "10000"

英文:

I'm trying to build my .net core 3.0 web api project but stuck on a statement last 4 days.
Here is my problem. I have a filtration model called "GridFilter" this model looks like this :

  1. public class GridFilter
  2. {
  3. public string Operator { get; set; }
  4. public string Field { get; set; }
  5. public object Value { get; set; }
  6. public object Value2 { get; set; }
  7. public string Logic { get; set; }
  8. }

in this model i keep Value and Value2 as object before filtering any model im converting this values to related column type via Universal Type Converter. I used this system in .netfreamwork working pretty well. But in .net core 3.0 when i did a request this model filling like this :
Model

  1. Operator: &quot;eq&quot;
  2. Logic: null
  3. Value: ValueKind = Number : &quot;10000&quot;
  4. Value2: null
  5. Field: &quot;SCT_CATEGORY&quot;

request:
{&quot;filter&quot;: {&quot;filters&quot;: [{&quot;field&quot;: &quot;SCT_CATEGORY&quot;, &quot;value&quot;: 10000, &quot;operator&quot;: &quot;eq&quot;}]}}

I searched straight 4 days and can't fix this. Im trying to fill it like this:

  1. Operator: &quot;eq&quot;
  2. Logic: null
  3. Value: 10000
  4. Value2: null
  5. Field: &quot;SCT_CATEGORY&quot;

How can i fix this problem.
Thanks!

EDIT

  1. [Route(&quot;[action]&quot;)]
  2. [HttpPost]
  3. public async Task&lt;Response&gt; List([FromBody]GridFilter request)

My ConfigureServices like this:

  1. services.AddControllers()
  2. .AddJsonOptions(o =&gt;
  3. {
  4. o.JsonSerializerOptions.PropertyNamingPolicy = null;
  5. o.JsonSerializerOptions.DictionaryKeyPolicy = null;
  6. });

and in this snippet im building my filter for fluent nhibarte

  1. internal static MyCriteria BuildFilter(ISession sess, GridFilter gf)
  2. {
  3. MyCriteria mc = null;
  4. var t = !string.IsNullOrEmpty(gf.Field)
  5. ? TypeHelper.GetType(typeof(T).GetProperty(gf.Field))
  6. : null;
  7. if (t == typeof(char) &amp;&amp; (!new[] { &quot;eq&quot;, &quot;neq&quot; }.Contains(gf.Operator)))
  8. {
  9. gf.Operator = &quot;eq&quot;;
  10. }
  11. switch (gf.Operator)
  12. {
  13. case &quot;eq&quot;:
  14. mc = gf.Value == null ? new MyCriteria { cr = Restrictions.IsNotNull(gf.Field), logic = gf.Logic.ToEnum(Logic.and) } : new MyCriteria { cr = Restrictions.Eq(gf.Field, ChangeType(gf.Value, t)), logic = gf.Logic.ToEnum(Logic.and) };
  15. break;...

And my change type methed like this:

  1. internal static object ChangeType(object value, Type conversionType)
  2. {
  3. try
  4. {
  5. object result;
  6. UniversalTypeConverter.TryConvert(value, conversionType, out result);
  7. return result;
  8. }
  9. catch (Exception)
  10. {
  11. return false;
  12. }
  13. }

at this point i need to convert &quot;10000&quot; not ValueKind = Number : &quot;10000&quot;

答案1

得分: 1

正如评论中所提到的,这种行为变化是因为.NET Core 3.0将其Json序列化引擎从Newtonsoft替换为System.Text.Json。

我看到有两个选择供您选择:

第一种选择是将默认的Json序列化器切换回Newtonsoft。如何执行此操作的详细信息在这里:https://stackoverflow.com/questions/55666826/where-did-imvcbuilder-addjsonoptions-go-in-net-core-3-0/55666898#55666898

第二种选择是编写您自己的自定义转换器。我可以想象这个转换器尝试解析所有已知类型,获取第一个成功的类型。例如,Int.TryParse,DateTime.TryParse等等。

英文:

As was said in one of the comments, this is change in behavior is due to .NET Core 3.0 replacing it's Json serialization engine from Newtonsoft to System.Text.Json .

I see two options for you:

First is to change the default Json serializer back to Newtonsoft. Details on how to do it are here : https://stackoverflow.com/questions/55666826/where-did-imvcbuilder-addjsonoptions-go-in-net-core-3-0/55666898#55666898

Second option is to write your own custom converter. I can imagine this converter trying to parse all known types, grabbing first that succeeds. Eg. Int.TryParse, DateTime.TryParse, etc..

答案2

得分: 0

以下是您要求的翻译部分:

  1. using Newtonsoft.Json;
  2. using System;
  3. using System.Collections.Generic;
  4. using System.Linq;
  5. static class Program
  6. {
  7. static void Main()
  8. {
  9. var request = "{\"filter\": {\"filters\": [{\"field\": \"SCT_CATEGORY\", \"value\": 10000, \"operator\": \"eq\"}]}}";
  10. var obj = JsonConvert.DeserializeObject<Request>(request);
  11. var filter = obj.Filter.Filters.Single();
  12. Console.WriteLine(filter.Operator); // "eq"
  13. Console.WriteLine(filter.Logic); // null
  14. Console.WriteLine(filter.Value); // 10000
  15. Console.WriteLine(filter.Value2); // null
  16. Console.WriteLine(filter.Field); // SET_CATEGORY
  17. }
  18. }
  19. public class Request // just to shape the json
  20. {
  21. public RequestFilters Filter { get; set; }
  22. }
  23. public class RequestFilters // just to shape the json
  24. {
  25. public List<GridFilter> Filters { get; } = new List<GridFilter>();
  26. }
  27. public class GridFilter
  28. {
  29. public string Operator { get; set; }
  30. public string Field { get; set; }
  31. public object Value { get; set; }
  32. public object Value2 { get; set; }
  33. public string Logic { get; set; }
  34. }

如果您还想能够保留大小写进行序列化,您需要告诉序列化程序:

  1. public class Request // just to shape the json
  2. {
  3. [JsonProperty("filter")]
  4. public RequestFilters Filter { get; set; }
  5. }
  6. public class RequestFilters // just to shape the json
  7. {
  8. [JsonProperty("filters")]
  9. public List<GridFilter> Filters { get; } = new List<GridFilter>();
  10. }
  11. public class GridFilter
  12. {
  13. [JsonProperty("operator")]
  14. public string Operator { get; set; }
  15. [JsonProperty("field")]
  16. public string Field { get; set; }
  17. [JsonProperty("value")]
  18. public object Value { get; set; }
  19. [JsonProperty("value2")]
  20. public object Value2 { get; set; }
  21. [JsonProperty("logic")]
  22. public string Logic { get; set; }
  23. }

希望这些对您有所帮助。

英文:

Hard so say much without your deserialize code, but: this works fine:

  1. using Newtonsoft.Json;
  2. using System;
  3. using System.Collections.Generic;
  4. using System.Linq;
  5. static class Program
  6. {
  7. static void Main()
  8. {
  9. var request = @&quot;{&quot;&quot;filter&quot;&quot;: {&quot;&quot;filters&quot;&quot;: [{&quot;&quot;field&quot;&quot;: &quot;&quot;SCT_CATEGORY&quot;&quot;, &quot;&quot;value&quot;&quot;: 10000, &quot;&quot;operator&quot;&quot;: &quot;&quot;eq&quot;&quot;}]}}&quot;;
  10. var obj = JsonConvert.DeserializeObject&lt;Request&gt;(request);
  11. var filter = obj.Filter.Filters.Single();
  12. Console.WriteLine(filter.Operator); // &quot;eq&quot;
  13. Console.WriteLine(filter.Logic); // null
  14. Console.WriteLine(filter.Value); // 10000
  15. Console.WriteLine(filter.Value2); // null
  16. Console.WriteLine(filter.Field); // SET_CATEGORY
  17. }
  18. }
  19. public class Request // just to shape the json
  20. {
  21. public RequestFilters Filter { get; set; }
  22. }
  23. public class RequestFilters // just to shape the json
  24. {
  25. public List&lt;GridFilter&gt; Filters { get; } = new List&lt;GridFilter&gt;();
  26. }
  27. public class GridFilter
  28. {
  29. public string Operator { get; set; }
  30. public string Field { get; set; }
  31. public object Value { get; set; }
  32. public object Value2 { get; set; }
  33. public string Logic { get; set; }
  34. }

If you also want to be able to serialize retaining the case, you'd need to tell the serializer:

  1. public class Request // just to shape the json
  2. {
  3. [JsonProperty(&quot;filter&quot;)]
  4. public RequestFilters Filter { get; set; }
  5. }
  6. public class RequestFilters // just to shape the json
  7. {
  8. [JsonProperty(&quot;filters&quot;)]
  9. public List&lt;GridFilter&gt; Filters { get; } = new List&lt;GridFilter&gt;();
  10. }
  11. public class GridFilter
  12. {
  13. [JsonProperty(&quot;operator&quot;)]
  14. public string Operator { get; set; }
  15. [JsonProperty(&quot;field&quot;)]
  16. public string Field { get; set; }
  17. [JsonProperty(&quot;value&quot;)]
  18. public object Value { get; set; }
  19. [JsonProperty(&quot;value2&quot;)]
  20. public object Value2 { get; set; }
  21. [JsonProperty(&quot;logic&quot;)]
  22. public string Logic { get; set; }
  23. }

huangapple
  • 本文由 发表于 2020年1月6日 14:59:27
  • 转载请务必保留本文链接:https://go.coder-hub.com/59607912.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定