. Net Core 3.0 объект Тип установленное значение - PullRequest
0 голосов
/ 06 января 2020

Я пытаюсь создать свой проект 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 в качестве объекта, прежде чем фильтровать любую модель, я преобразую эти значения в связанный тип столбца с помощью Универсальный конвертер типов . Я использовал эту систему в .netfreamwork, работая довольно хорошо. Но в. 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;
                });

и в этом фрагменте я собираю мой фильтр для беглого 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) && (!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;...

И мой тип изменения метнулся следующим образом:

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"

Ответы [ 2 ]

0 голосов
/ 06 января 2020

Как было сказано в одном из комментариев, это изменение в поведении происходит из-за. NET Core 3.0 заменяет свой Json механизм сериализации с Newtonsoft на System.Text. Json.

Я вижу два варианта для вас:

Первый - изменить сериализатор по умолчанию Json обратно на Newtonsoft. Подробности о том, как это сделать, можно найти здесь: Откуда IMvcBuilder AddJsonOptions go in. Net Core 3.0?

Второй вариант - написать собственный пользовательский конвертер . Я могу представить, как этот конвертер пытается проанализировать все известные типы, сначала получая успешный захват. Например. Int.TryParse, DateTime.TryParse, et c ..

0 голосов
/ 06 января 2020

Трудно сказать так много без десериализованного кода, но: это прекрасно работает:

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; }
}
...