7

コードで API からの応答を取得する際に問題が発生しています。要求はタイムアウトせず、まったく応答がありません。私は自分のAPIでAPIエンドポイントを作成してjson文字列を返し、「Firefox Poster」を使用してjsonデータを手動で投稿しましたが、問題なく動作しました。これで、問題は私のコードのどこかにあると思います。

Angular フロントエンドで使用するために開発中の C# WebAPI を取得しました (これは機能しますが、履歴用です)。API を呼び出すときに、オブジェクト「EnrollmentRequestDto」を作成します

public class EnrollmentRequestDto
{
    /// <summary>
    /// Context Information for the request. Contains the Ship-To, language code and timezone.
    /// </summary>
    [JsonProperty("requestContext")]
    public RequestContextDto RequestContext { get; set; }
    /// <summary>
    /// Unique ID provided by DEP to reseller on provisioning DEP access. This would be the reseller's DEP ID if its posted by distributor OBO a reseller, and would be his own depResellerId if a reseller is posting for self.
    /// </summary>
    [JsonProperty("depResellerId")]
    public string DepResellerId { get; set; }
    /// <summary>
    /// Unique transaction ID provided by the reseller
    /// </summary>
    [JsonProperty("transactionId")]
    public string TransactionId { get; set; }
    /// <summary>
    /// List of orders in the transaction (limit 1000 per transaction)
    /// </summary>
    [JsonProperty("orders")]
    public List<OrderDto> Orders { get; set; }
}

このオブジェクトが作成された後、クラス RequestHandler とメソッド BulkEnrollRequest に送信します。この atm は HttpClient 拡張 Flurl で記述されており、次の場所にあります: github

public IResponse BulkEnrollRequest(EnrollmentRequestDto enrollmentRequest)
    {
        try
        {
            var result = _bulkEnrollUrl.PostJsonAsync(enrollmentRequest).ReceiveJson<SuccessResponse>();
            result.Wait();
            return result.Result;
        }
        catch (FlurlHttpTimeoutException)
        {
            throw new AppleTimeOutException();
        }
        catch (FlurlHttpException ex)
        {
            return _errorHandler.DeserializeFlurlException(ex);
        }
    }

Flurlで何も起こらないことを確認するためにこれも試しました(これは、応答を取得したいポイントまでデバッグするためです):

public async Task<IResponse> BulkEnrollRequest(EnrollmentRequestDto enrollmentRequest)
    {
        var json = JsonConvert.SerializeObject(enrollmentRequest);

        var httpClient = new HttpClient();
        httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
        HttpResponseMessage response = await httpClient.PostAsync(_bulkEnrollUrl, new StringContent(json, Encoding.UTF8, "application/json"));

        return new SuccessResponse();
    }

そして、コードは await ポイントでフリーズし、何も起こりません。BulkEnrollRequest の後にブレークポイントを配置しようとしたため、このメソッドから離れることはありません。

ここで面白い部分があります。ErrorHandler の作業中には機能しましたが、ある時点で API が応答を停止しました。Wireshark は、リクエストが行われていることを示しています。

どんな助けでも大歓迎です。

編集

これで動作します!API コントローラーから RequestHandler まで非同期を実装し、すべての呼び出しを待機しました。参考のため:

public async Task<IResponse> BulkEnrollRequest(EnrollmentRequestDto enrollmentRequest)
    {
        try
        {
            var result = await _bulkEnrollUrl.PostJsonAsync(enrollmentRequest).ReceiveJson<SuccessResponse>();
            return result;
        }
        catch (FlurlHttpTimeoutException)
        {
            throw new AppleTimeOutException();
        }
        catch (FlurlHttpException ex)
        {
            return _errorHandler.DeserializeFlurlException(ex);
        }
    }
4

2 に答える 2

5

これは修正されました。Wireshark トラフィックが非常に奇妙に見える理由は、コードのデッドロックが原因であり、タイムアウトは私の側にあったため、情報を FIN ACK できませんでした。これを修正するために、Controller から RequestHandler クラスまで、すべてのメソッドにasyncを実装しました。参考のため:

public async Task<IResponse> BulkEnrollRequest(EnrollmentRequestDto enrollmentRequest)
    {
        try
        {
            var result = await _bulkEnrollUrl.PostJsonAsync(enrollmentRequest).ReceiveJson<SuccessResponse>();
            return result;
        }
        catch (FlurlHttpTimeoutException)
        {
            throw new AppleTimeOutException();
        }
        catch (FlurlHttpException ex)
        {
            return _errorHandler.DeserializeFlurlException(ex);
        }
    }
于 2015-09-11T07:08:00.527 に答える
0

このコードを試してください

インストール パッケージ Microsoft.AspNet.WebApi.Client

 using (var client = new HttpClient())
        {
            client.BaseAddress = new Uri("http://localhost:9000/");
            client.DefaultRequestHeaders.Accept.Clear();
            client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));

            HttpResponseMessage response = await client.PostAsJsonAsync("api/products", enrollmentRequest);
            if (response.IsSuccessStatusCode)
            {
                var result = await response.Content.ReadAsAsync<T>();
            }
        }
于 2015-09-10T12:30:46.747 に答える