.Net Core 3.0 对象类型设置值

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

.Net Core 3.0 object Type set value

问题

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

public class GridFilter
{
     public string Operator { get; set; }
     public string Field { get; set; }
     public object Value { get; set; }
     public object Value2 { get; set; }
     public string Logic { get; set; }
}

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

Operator: "eq"
Logic: null
Value: ValueKind = Number : "10000"
Value2: null
Field: "SCT_CATEGORY"

请求:

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

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

Operator: "eq"
Logic: null
Value: 10000
Value2: null
Field: "SCT_CATEGORY"

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

编辑

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

我的ConfigureServices配置如下:

services.AddControllers()
    .AddJsonOptions(o =>
    {
        o.JsonSerializerOptions.PropertyNamingPolicy = null;
        o.JsonSerializerOptions.DictionaryKeyPolicy = null;
    });

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

internal static MyCriteria BuildFilter(ISession sess, GridFilter gf)
{
    MyCriteria mc = null;
    var t = !string.IsNullOrEmpty(gf.Field)
        ? TypeHelper.GetType(typeof(T).GetProperty(gf.Field))
        : null;

    if (t == typeof(char) && (!new[] { "eq", "neq" }.Contains(gf.Operator)))
    {
        gf.Operator = "eq";
    }

    switch (gf.Operator)
    {
        case "eq":
            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) };
            break;
        // 还有其他操作符的处理...
    }
    // ...
}

我的ChangeType方法如下:

internal static object ChangeType(object value, Type conversionType)
{
    try
    {
        object result;
        UniversalTypeConverter.TryConvert(value, conversionType, out result);
        return result;
    }
    catch (Exception)
    {
        return false;
    }
}

在这一点上,我需要转换的是"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 :

    public class GridFilter
    {
         public string Operator { get; set; }
         public string Field { get; set; }
         public object Value { get; set; }
         public object Value2 { get; set; }
         public string Logic { get; set; }
    }

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

Operator: &quot;eq&quot;
Logic: null
Value: ValueKind = Number : &quot;10000&quot;
Value2: null
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:

Operator: &quot;eq&quot;
Logic: null
Value: 10000
Value2: null
Field: &quot;SCT_CATEGORY&quot;

How can i fix this problem.
Thanks!

EDIT

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

My ConfigureServices like this:

services.AddControllers()
                .AddJsonOptions(o =&gt;
                {
                    o.JsonSerializerOptions.PropertyNamingPolicy = null;
                    o.JsonSerializerOptions.DictionaryKeyPolicy = null;
                });

and in this snippet im building my filter for fluent nhibarte

  internal static MyCriteria BuildFilter(ISession sess, GridFilter gf)
    {
        MyCriteria mc = null;
        var t = !string.IsNullOrEmpty(gf.Field)
            ? TypeHelper.GetType(typeof(T).GetProperty(gf.Field))
            : null;

        if (t == typeof(char) &amp;&amp; (!new[] { &quot;eq&quot;, &quot;neq&quot; }.Contains(gf.Operator)))
        {
            gf.Operator = &quot;eq&quot;;
        }

        switch (gf.Operator)
        {
            case &quot;eq&quot;:
                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) };
                break;...

And my change type methed like this:

internal static object ChangeType(object value, Type conversionType)
        {
            try
            {
                object result;
                UniversalTypeConverter.TryConvert(value, conversionType, out result);
                return result;
            }
            catch (Exception)
            {
                return false;
            }
        }

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

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

using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;

static class Program
{
    static void Main()
    {
        var request = "{\"filter\": {\"filters\": [{\"field\": \"SCT_CATEGORY\", \"value\": 10000, \"operator\": \"eq\"}]}}";
        var obj = JsonConvert.DeserializeObject<Request>(request);
        var filter = obj.Filter.Filters.Single();
        Console.WriteLine(filter.Operator); // "eq"
        Console.WriteLine(filter.Logic); // null
        Console.WriteLine(filter.Value); // 10000
        Console.WriteLine(filter.Value2); // null
        Console.WriteLine(filter.Field); // SET_CATEGORY
    }
}
public class Request // just to shape the json
{
    public RequestFilters Filter { get; set; }
}
public class RequestFilters // just to shape the json
{
    public List<GridFilter> Filters { get; } = new List<GridFilter>();
}
public class GridFilter
{
    public string Operator { get; set; }
    public string Field { get; set; }
    public object Value { get; set; }
    public object Value2 { get; set; }
    public string Logic { get; set; }
}

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

public class Request // just to shape the json
{
    [JsonProperty("filter")]
    public RequestFilters Filter { get; set; }
}
public class RequestFilters // just to shape the json
{
    [JsonProperty("filters")]
    public List<GridFilter> Filters { get; } = new List<GridFilter>();
}
public class GridFilter
{
    [JsonProperty("operator")]
    public string Operator { get; set; }
    [JsonProperty("field")]
    public string Field { get; set; }
    [JsonProperty("value")]
    public object Value { get; set; }
    [JsonProperty("value2")]
    public object Value2 { get; set; }
    [JsonProperty("logic")]
    public string Logic { get; set; }
}

希望这些对您有所帮助。

英文:

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

using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;

static class Program
{
    static void Main()
    {
        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;;
        var obj = JsonConvert.DeserializeObject&lt;Request&gt;(request);
        var filter = obj.Filter.Filters.Single();
        Console.WriteLine(filter.Operator); // &quot;eq&quot;
        Console.WriteLine(filter.Logic); // null
        Console.WriteLine(filter.Value); // 10000
        Console.WriteLine(filter.Value2); // null
        Console.WriteLine(filter.Field); // SET_CATEGORY
    }
}
public class Request // just to shape the json
{
    public RequestFilters Filter { get; set; }
}
public class RequestFilters // just to shape the json
{
    public List&lt;GridFilter&gt; Filters { get; } = new List&lt;GridFilter&gt;();
}
public class GridFilter
{
    public string Operator { get; set; }
    public string Field { get; set; }
    public object Value { get; set; }
    public object Value2 { get; set; }
    public string Logic { get; set; }
}

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

public class Request // just to shape the json
{
    [JsonProperty(&quot;filter&quot;)]
    public RequestFilters Filter { get; set; }
}
public class RequestFilters // just to shape the json
{
    [JsonProperty(&quot;filters&quot;)]
    public List&lt;GridFilter&gt; Filters { get; } = new List&lt;GridFilter&gt;();
}
public class GridFilter
{
    [JsonProperty(&quot;operator&quot;)]
    public string Operator { get; set; }
    [JsonProperty(&quot;field&quot;)]
    public string Field { get; set; }
    [JsonProperty(&quot;value&quot;)]
    public object Value { get; set; }
    [JsonProperty(&quot;value2&quot;)]
    public object Value2 { get; set; }
    [JsonProperty(&quot;logic&quot;)]
    public string Logic { get; set; }
}

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:

确定