Передача словаря в QueryParameters с использованием маршрутизации - PullRequest
0 голосов
/ 12 февраля 2020

Я хочу передать словарь через контроллер с помощью. Net Web Api.

К сожалению, он не работает, как описано в Документы Microsoft .

Мой код выглядит следующим образом:

[HttpGet]
[Route("{key}")]
public ResponseType SearchObjects([FromUri] string key, 
    [FromUri]Dictionary<string, string> options) {}

Параметр 'index' работает, но параметр 'options' всегда пуст (длина = 0) ...

Запросы, которые я пытался на данный момент:

http://localhost/key?index=1&filter [foo] = бар

http://localhost/key?index=1&filter [ 'foo'] = бар

http://localhost/key?index=1&filter.foo=bar

Кто-нибудь видит, что мне не хватает? Есть ли какие-либо шаги для отладки / симуляции сериализации?

Ответы [ 2 ]

0 голосов
/ 13 февраля 2020

Мое решение сейчас немного хакерское, но, похоже, в настоящее время нет лучшего способа ...

Как и раньше, есть параметр Method. Чтобы обойти проблему, заключающуюся в том, что Web Api не заполняет словарь автоматически, я реализовал свой собственный метод ... (Если Web Api сделает это в более позднем выпуске, будет просто удалить метод, и все должно работать тогда ...

[HttpGet]
[Route("{key}")]
public ResponseType SearchObjects([FromUri] string key, [FromUri] Dictionary<string, string> options)
{
    AddMatchingQueryParamsToDictionary(Request, nameof(options), options);
    //options are now ready to use
}


/// <summary>
/// Fills the dictionary with additional values found in query parameters
/// In the query parameters given by the request, dictionary items will be in the format "dictName.dictKey".
/// </summary>
private static void AddMatchingQueryParamsToDictionary(HttpRequestMessage request, string dictionaryModelName, IDictionary<string, string> dictionaryToFill)
{
    var queryParams = request.GetQueryNameValuePairs();
    queryParams
        .Where(pair => pair.Key.StartsWith(dictionaryModelName))
        .Select(pair =>
        {
            var key = pair.Key;
            var index = key.IndexOf(dictionaryModelName, StringComparison.InvariantCultureIgnoreCase);
            var newKey = index < 0 ? key : key.Remove(index, dictionaryModelName.Length + 1 /*the dot*/);
            return (key: newKey, value: pair.Value);
        }).ToList()
        .ForEach(pair => dictionaryToFill[pair.key] = pair.value);
}

Что вы думаете об этом решении?

0 голосов
/ 12 февраля 2020

Вы можете использовать JSON! Просто добавьте пакет Newtonsoft.Json

Что-то вроде:

    [HttpGet("{json}")]
    public async Task<IActionResult> GetAsync([FromRoute] string json)
    {
        var dictionary = JsonConvert.DeserializeObject<IDictionary<string, string>>(json);
        return await Task.FromResult(Ok());
    }

РЕДАКТИРОВАТЬ:

Пример JSON:

{ "Key1": "Value1", "Key2": "Value2", "Key3": "Value3" }
...