2017-02-07 15 views
2

Hy ya'll,Json сообщение через HttpClient mvvmcross

У меня есть проблема с отправкой POST в формате JSON через HttpClient объект в растворе MVVMCROSS (Xamarin) MVVMCROSS просто рамки Model View ViewModel для кросс-платформенной Е.А. Droid, IOS, Windows и т.д.

Таким образом, решение, как это:

--Core (where I have my ViewModels and Services) 
--Droid (Android Layout etc) 
--iOS (Not used currently) 

внутри ядра у меня есть свои классы услуг, которые я инициализировать через IoC (Инверсия управления, что-то вроде инъекции зависимостей)

У меня есть этот удивительный классный API, который я могу использовать с помощью запроса JSON Post. API делает распознавание лица и отправляет обратно «настроение» лица (Злой, нейтральный, счастливый и т.д.)

Чтобы использовать этот мой JSON должен выглядеть следующим образом

{ 
    "url" : "http://previews.123rf.com/images/kadettmann/kadettmann1508/kadettmann150800099/43824672-Handsome-argentinian-guy-at-beach-Stock-Photo-happy.jpg" 
} 

До сих пор так хорошо, теперь URL POST: https://api.projectoxford.ai/emotion/v1.0/recognize Кажется, не сложно, я думаю!

мне также нужно отправить два заголовка:

Content-Type = application/json 
Ocp-Apim-Subscription-Key = My super awesome secret key 

Если это отправить этот JSON через Почтальон (Chrome плагин) Я получаю ожидаемый результат:

[ 
    { 
    "faceRectangle": { 
     "height": 312, 
     "left": 563, 
     "top": 208, 
     "width": 312 
    }, 
    "scores": { 
     "anger": 0.00000000112, 
     "contempt": 0.000000049, 
     "disgust": 0.0000000035, 
     "fear": 0.000000000106, 
     "happiness": 0.99999994, 
     "neutral": 0.000000000238, 
     "sadness": 0.00000000005, 
     "surprise": 0.00000000160 
    } 
    } 
] 

Так что теперь я пытаюсь сделать приложение MVVMCROSS для Android и iOS, которое отправляет этот JSON на сервер Microsoft.

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

public async Task<bool> RestRequestSucces(string secret, string jsonSerialized) 
{ 
    bool result = false;  

    try 
    { 
     HttpResponseMessage response; 

     using (var httpClient = new HttpClient()) 
     { 
      var request = new StringContent(jsonSerialized); 
      request.Headers.ContentType = new MediaTypeHeaderValue("application/json"); 

      httpClient.DefaultRequestHeaders.Add("Ocp-Apim-Subscription-Key", secret); 

      response = await httpClient.PostAsync(new Uri("https://api.projectoxford.ai/emotion/v1.0/recognize"), request); 

      result = true; 
     } 
    } 
    catch (Exception e) 
    { 
     string error = e.Message; 
     result = false; 
    } 
    return result; 
} 

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

public class URLObject 
{ 
    public string url { get; set; } 
} 

Для сериализации объекта я использую этот

private IMvxJsonConverter serializer = Mvx.Resolve<IMvxJsonConverter>(); 
serializer.SerializeObject(urlObject); 

Но в response = await httpClient.PostAsync мой код зависает. Это не идет дальше.

я вызываю метод RestRequestSucces так:

IRestService restService = Mvx.Resolve<IRestService>(); 
restService.RestRequestSucces(secret, jsonSerialized); 

Все это происходит внутри проекта Core.

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

... 
    <uses-permission android:name="android.permission.INTERNET" /> 
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> 
    <application android:label="@string/ApplicationName" android:icon="@drawable/Icon" android:theme="@style/MyTheme"></application> 
</manifest> 

Если кто-то может показать мне, как только POST «простой» JSON через MVVMCROSS внутри проекта CORE, что было бы удивительным !!

+0

Этот вопрос не имеет ничего общего с MvvmCross. Это просто HttpClient и Json. Вы могли бы упростить его. Вы поставили точку прерывания в выводе catch, чтобы понять, что не так? – xleon

+0

Также попробуйте следующее: новый StringContent (jsonSerialized, Encoding.UTF8, «application/json») – xleon

+0

Я уже сделал это, получается, что «HttpClient» имеет проблемы с некоторыми сайтами TLS/SSL, не зная почему. Вместо этого я использовал «ModernHttpClient», и проблема решена, см. Мой ответ – Igoranze

ответ

1

решаемые это сам,

Оказывается HttpClient имеет проблемы с некоторыми TLS/SSL веб-сайт (HTTPS). Просто используя ModernHttpClient решил мою проблему!

Остальная часть кода остается тем же самым, только HttpClient конструктор отличается

using (var httpClient = new HttpClient(new NativeMessageHandler())) 
{ 
    .... 
} 

NativeMessageHandler является HttpClientHandler и могут быть найдены в ModernHttpClient, код выглядит следующим образом:

namespace ModernHttpClient 
{ 
    public class NativeMessageHandler : HttpClientHandler 
    { 
     public NativeMessageHandler(); 
     public NativeMessageHandler(bool throwOnCaptiveNetwork, bool customSSLVerification, NativeCookieHandler cookieHandler = null); 

     public bool DisableCaching { get; set; } 

     public void RegisterForProgress(HttpRequestMessage request, ProgressDelegate callback); 
     [AsyncStateMachine(typeof(<SendAsync>c__async0))] 
     [DebuggerStepThrough] 
     protected override Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken); 
    } 
} 

Надеюсь, вы, ребята, можете это использовать! Ссылка на ModernHttpClient на github.