jsakamoto / self-learning-materials-for-blazor-jp

C# で Single Page Web アプリを開発するフレームワーク「Blazor」の WebAssembly 版の自習教材です。
https://jsakamoto.github.io/self-learning-materials-for-blazor-jp/Blazor%E3%82%A2%E3%83%97%E3%83%AA%E3%82%B1%E3%83%BC%E3%82%B7%E3%83%A7%E3%83%B3%E3%83%97%E3%83%AD%E3%82%B0%E3%83%A9%E3%83%9F%E3%83%B3%E3%82%B0%E8%87%AA%E7%BF%92%E6%9B%B8-v.8.0.0.pdf
The Unlicense
141 stars 8 forks source link

HttpRequestException の catch について #12

Closed pecochappy closed 3 years ago

pecochappy commented 3 years ago

動作環境の違いによるものかもしれませんが

public async Task<Device> GetDeviceAsync(Guid id)
{
    try
    {
        return await HttpClient.GetFromJsonAsync<Device>($"api/devices/{id}");
    }
    catch (HttpRequestException e) when (e.Message == "404 (Not Found)")
    {
        return null;
    }
}

の例外箇所を確認してみたところ、HttpRequestException の Message が 404 (Not Found) ではなく Response status code does not indicate success: 404 (Not Found). であったため、catch できませんでした。

※when (e.StatusCode == HttpStatusCode.NotFound) としたら catch できました。

jsakamoto commented 3 years ago

@pecochappy 重ね重ねフィードバックありがとうございます!

これは .NET 5 で例外メッセージが変わってしまったのが原因ですが、その他にも、.NET Core 当時は、なんと、HttpRequestException から HTTP ステータスコードが取得できないという仕様で、それでこんなコードで妥協したのが敗因ですね...。 (かといって GetFromJsonAsync<T>() を使わずに GetAsync() で生のレスポンスを得てからステータスコードを見たり自分でJSONデシリアライズしたりするのも、どうかと思い...)

※when (e.StatusCode == HttpStatusCode.NotFound) としたら catch できました。

そうですね、.NET 5 からはお知らせ頂いたコードで安全に書けますね。

自習書ならびにソースコード改訂して、追ってリリースしたいと思います。

jsakamoto commented 3 years ago

修正版 (v.5.0b) をリリースしました。

pecochappy commented 3 years ago

ソースコード該当箇所が修正されたことを確認致しました。 普段は .NET Framework で開発を行っており、.NET Core の HttpRequestException から StatusCode が取得できなかったことは知りませんでした。なかなか実装者に厳しい制約ですね。。。 .NET 5 で機能が充実したようで良かったです。

ご対応頂きありがとうございます。