Пользовательский заголовок принятия не работает на Windows Phone 8

У меня есть класс в переносимой библиотеке классов (ориентированный на .NET 4.5 и Windows Phone 8.1), который использует класс HttpClient (System.Net.Http.HttpClient) для отправки строки в веб-службу. Служба требует, чтобы я установил заголовок Accept в запросе, чтобы указать версию API следующим образом:

Accept: vnd.servicehost.v1+json

Я пробовал это в своем классе следующим образом:

_httpClient.DefaultRequestHeaders.Add("Accept", "vnd.servicehost.v1+json");

И он выдает исключение FormatException, указывающее, что мой заголовок Accept недействителен. Итак, я пытаюсь настроить его следующим образом:

_httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("vnd.servicehost.v1+json"));

И он по-прежнему выдает FormatException. Я нашел этот ответ, который убедил меня попробовать использовать метод TryAddWithoutValidation() следующим образом:

_httpClient.DefaultRequestHeaders.TryAddWithoutValidation("Accept", "vnd.servicehost.v1+json");

Наконец, я не получаю FormatException! Мой метод post работает, когда я вызываю его из своего тестового проекта модуля/интеграции .NET 4.5. Я получаю 200 с данными, которые я ожидал. Однако, когда я вызываю тот же метод из своего Windows Phone 8.1 (или эмулятора), служба отвечает, сообщая мне, что версия, указанная в моем запросе, недействительна.

Я не могу понять, как заставить Fiddler показать мне трафик от моего эмулятора Windows Phone, чтобы увидеть, как выглядит фактический запрос. Я предполагаю, что заголовок Accept никогда не добавляется. Я надеюсь, что опытный разработчик Windows Phone сможет распознать какую-то очевидную ошибку, которую я совершаю...


person Tom Faltesek    schedule 12.02.2015    source источник


Ответы (3)


Вы можете использовать Windows.Web.Http.HttpClient вместо System.Net.Http.HttpClient, т.е.:

HttpClient _httpClient = new HttpClient();
bool result = _httpClient.DefaultRequestHeaders.TryAppendWithoutValidation("Accept", "vnd.servicehost.v1+json");
var response = await _httpClient.GetAsync(uri);
person kiewic    schedule 12.02.2015
comment
Спасибо за предложение. Я не думаю, что у меня есть доступ к Windows.Web.Http.HttpClient при работе с .NET 4.5. - person Tom Faltesek; 13.02.2015

В windows phone 8 можно использовать WebClient для этого, например:

        WebClient clt = new WebClient();
        clt.Headers["Content-Type"] = "application/json";
        clt.Headers["Accept"] = "vnd.servicehost.v1+json";
        clt.UploadStringAsync(new Uri(uri, "{}");

ПРИМЕЧАНИЕ. Я не уверен в этом, так как не проверял, но вы можете попробовать

person Dev    schedule 12.02.2015
comment
Спасибо за предложение. Я не думаю, что у меня есть доступ к WebClient при работе с Windows Phone 8.1. - person Tom Faltesek; 13.02.2015

В моей библиотеке Windows Phone/Windows я использую

client.DefaultRequestHeaders.TryAddWithoutValidation()

и это работает нормально. Так что ваши

_httpClient.DefaultRequestHeaders.TryAddWithoutValidation("Accept", "vnd.servicehost.v1+json");

тоже должно быть нормально. Единственный способ узнать наверняка — увидеть фактический трафик с телефона на сервер.

Заставить Fiddler работать с эмулятором не так просто (мне так и не удалось этого сделать), но захват трафика с реального устройства довольно прост.

В настройках Fiddler необходимо разрешить удаленные подключения и перезапустить Fiddler. Затем в устройстве убедитесь, что вы подключены к той же сети, что и ваш компьютер, и в настройках WiFi установите прокси-сервер на your_computer_ip:8888. Теперь весь трафик должен проходить через Fiddler, и вы увидите, нормально ли выглядят http-запросы.

person Igor Kulman    schedule 12.02.2015
comment
Игорь, спасибо за предложение. Кажется, я не могу заставить ваше прокси-решение работать. У меня есть Fiddler, настроенный так, как вы описываете. Я пробовал изменить порт на случай коллизии или чего-то еще. Я попытался отключить брандмауэр на своем компьютере. - person Tom Faltesek; 13.02.2015