Lightning Blog
Blazor記事イメージ画像

【Blazor】 SignalRのまとめ

更新日:2024/08/06
Blazor Serverは、SignalRを常時接続を前提としたアプリケーションなので、SignalRにある程度知っておく必要があります。 この記事では、Blazor ServerのSignalRについて解説します。

    目次

  • SignalRとは?
  • SignalRを切断してみる1
  • SignalRを切断してみる2
  • SignalRの接続オプションをカスタマイズする
  • まとめ

SignalRとは?

セクション画像

SignalRは、ブラウザ-Webサーバ間で、リアルタイムで双方向通信を可能にするための仕組みです。

通常ブラウザからWebサーバーへリクエストを送信し、返却されたレスポンスをブラウザ側へ反映するのに対し、

SignalRでは、常時接続されているため、サーバーからブラウザへ直接データを反映することができます。

title%20%E9%80%9A%E5%B8%B8%0A%0A%E3%83%96%E3%83%A9%E3%82%A6%E3%82%B6-%3E%E3%82%B5%E3%83%BC%E3%83%90%E3%83%BC%3A%20%E3%83%AA%E3%82%AF%E3%82%A8%E3%82%B9%E3%83%88%0A%E3%83%96%E3%83%A9%E3%82%A6%E3%82%B6%3C-%E3%82%B5%E3%83%BC%E3%83%90%E3%83%BC%3A%20%E3%83%AC%E3%82%B9%E3%83%9D%E3%83%B3%E3%82%B9%0Aブラウザサーバー通常リクエストレスポンス title%20SignalR%0A%0A%E3%83%96%E3%83%A9%E3%82%A6%E3%82%B6%3C-%3E%E3%82%B5%E3%83%BC%E3%83%90%E3%83%BC%3A%20%E5%B8%B8%E6%99%82%E6%8E%A5%E7%B6%9A%0A%E3%83%96%E3%83%A9%E3%82%A6%E3%82%B6%3C--%E3%82%B5%E3%83%BC%E3%83%90%E3%83%BC%3A%20%E3%83%96%E3%83%A9%E3%82%A6%E3%82%B6%E3%81%B8%E3%83%87%E3%83%BC%E3%82%BF%E9%80%81%E4%BF%A1%0A%0A%0AブラウザサーバーSignalR常時接続ブラウザへデータ送信

Blazorでは、このSignalRをASP.NET Core SignalRというライブラリを使って実装しています。 詳細は公式ドキュメントから確認することができます。

公式ドキュメントはこちら

SignalRを切断してみる1

セクション画像

ネットワーク環境が悪い場所では、SignalRの接続が切れる可能性があります。 SignalRの接続が切れたときの挙動をテストするには、ローカル環境では再現が難しいです。

そこでコードを実行して疑似的に回線を切断することで、切断時の挙動を再現することができます。

以下サンプルコードになります。


@page "/"
@inject IJSRuntime JSRuntime

<button class="btn btn-primary d-block mb-3" @onclick="ForceCloseConnectionAsync">SignalR切断(再接続の設定がされている場合は、切断後に再接続を試みる)</button>

@code{
    /// <summary>
    ///  SignalRの接続を切断(ただし、再接続の設定がされている場合は、切断後に再接続を試みる)
    /// </summary>
    private async Task ForceCloseConnectionAsync()
    {
        await JSRuntime.InvokeVoidAsync("forceCloseConnection");
    }
}

/*
    SignalRの接続を切断(ただし、再接続の設定がされている場合は、切断後に再接続を試みる)
*/
function forceCloseConnection() {
    Blazor._internal.forceCloseConnection();
};

SignalRを切断するには、javascriptを呼ぶ必要があります。Blazorからjavascriptを呼びだす方法については、以下の記事を参照してください。

カード画像
JavaScriptを呼び出し方

BlazorでWEB開発は主にHTML, CSS, C#を使用しますが、JavaScriptの利用も避けられない場面がある。JavaScriptをBlazor内で呼び出すためには、IJSRuntimeサービスを利用する。IJSRuntimeを用いることで、C#からJavaScriptの関数を非同期的に実行可能。例として、ボタンクリックでJavaScriptのアラートを表示する方法を説明。BlazorでのJavaScript使用は最小限に留めるべきだが、必要な場面での知識は重要。

更新日:2023/07/19

javascriptでBlazor._internal.forceCloseConnection();が呼び出すと、SignalRを切断することができます。

実際にSignalRを切断してみると以下のようになります。

SignalR切断動作確認1

デフォルトでは、SignalRを切断すると、自動で再接続を試みる仕様になっています。 白いモーダル画面は、再接続を試みている画面になります。

このようにして、SignalRの接続が切れた際の挙動をテストすることができます。


SignalRを切断してみる2

セクション画像

前セクションではSignalRを切断すると、自動的に再接続を試みていましたが、 切断後に再接続を行わない方法もあります。

以下サンプルコードになります。


@page "/"
@inject IJSRuntime JSRuntime

<button class="btn btn-primary d-block mb-3" @onclick="DisconnectAsync">SignalR切断(再接続の設定がされていても、再接続されない)</button>

@code{
    /// <summary>
    /// SignalRの接続を切断(再接続の設定がされていても、再接続されない)
    /// </summary>
    private async Task DisconnectAsync()
    {
        await JSRuntime.InvokeVoidAsync("disconnect");
    }
}

/*
    SignalRの接続を切断(再接続の設定がされていても、再接続されない)
*/
function disconnect() {
    Blazor.disconnect();
}

前セクションと異なるのは、javascriptでBlazor.disconnect();が呼ばれている事です。この関数の場合は、SignalRを切断する点は同じですが、切断後に再接続を試みません。

実際にSignalRを切断してみると以下のようになります。

SignalR切断動作確認2

ボタンを押下すると、SignalRは切断されますが、再接続を試みる白いモーダルは表示されません。

SignalRが切断されている状態なので、Blazorを操作しようとすると、当然ですがエラーになります。


SignalRの接続オプションをカスタマイズする

セクション画像

Blazorでは、アプリケーションを開始した際に、デフォルト設定でSignalRが自動的に接続されます。

これを自動接続するのではなく、javascriptから明示的にSignalRを接続することで、オプションを設定することができます。

まず、SignalRの自動接続を無効にします。以下サンプルコードになります。


@using Microsoft.AspNetCore.Components.Web
@namespace Blazor_SignalR.Pages
@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <base href="~/" />
    <link rel="stylesheet" href="css/bootstrap/bootstrap.min.css" />
    <link href="css/site.css" rel="stylesheet" />
    <link href="Blazor_SignalR.styles.css" rel="stylesheet" />
    <component type="typeof(HeadOutlet)" render-mode="ServerPrerendered" />
</head>
<body>
    @RenderBody()

    <div id="blazor-error-ui">
        <environment include="Staging,Production">
            An error has occurred. This application may no longer respond until reloaded.
        </environment>
        <environment include="Development">
            An unhandled exception has occurred. See browser dev tools for details.
        </environment>
        <a href="" class="reload">Reload</a>
        <a class="dismiss">🗙</a>
    </div>

    @* 以下scriptタグにautostart=falseの属性を付与する *@
    <script src="_framework/blazor.server.js" autostart="false"></script>
    <script src="js/signalr.js"></script>
</body>
</html>

_framework/blazor.server.jsautostart="false"を付与することで、SignalRが自動接続されなくなります。

続いて、SignalRを接続するコードを書いていきます。以下サンプルコードになります。


/* 
    Blazorを手動で開始(SignalRを接続する)
    事前に_Layout.cshtml の以下の箇所を修正する必要あり(autostart="false" 属性を追加)
    <script src="_framework/blazor.server.js"></script> → <script src="_framework/blazor.server.js" autostart="false"></script>
*/
Blazor.start({
    reconnectionOptions: {
        maxRetries: 3,                      // SignalRが切れた場合、再接続の最大試行回数
        retryIntervalMilliseconds: 2000,    // どのくらい感覚を空けて再接続を試みるか(単位:ミリ秒)
    }
});

Blazor.startメソッドを実行することで、SignalRを接続することができます。 また、引数を設定することで、SignalRが切断された際のオプションを設定することができます。

maxRetriesは、再接続を最大何回までチャレンジするかを指定できます。今回は最大3回に設定しています。

retryIntervalMillisecondsは、どのくらい間隔で再接続チャレンジを行うかを指定できます。 今回は2000ミリ秒に設定しています。

SignalRを切断してみると、以下のような画面になります。

SignalR切断動作確認3

画像の赤枠部分には、コードで指定した再接続の最大試行回数が表示されるため、3になっています。 ちなみにデフォルトは8です。


まとめ

セクション画像

今回はSignalRについて解説しました。 案件によっては、SignalRのカスタマイズが必要になる場合もありますので、参考にしてみてください。


ブログ内の記事で書かれているサンプルコードは、GitHubから確認する事ができます。 是非参考にしてみてください。

この本では、Blazorの基本から高度なテクニックまで、実際のプロジェクトに役立つ知識を網羅しています。 初心者から経験者まで、Blazorを扱うすべての開発者にとっての必読書です。 この記事の執筆者も参考にした「Blazor入門」で、あなたのBlazorスキルを飛躍的に向上させませんか?

合わせて読みたい

カード画像
DOMイベント一覧

この記事では、Blazorで使用可能なDOMイベントに関する包括的なガイドを提供しています。DOM(Document Object Model)はウェブページの内容や構造を表現するための仕組みであり、Blazorを用いることで、さまざまなDOMイベントを効果的に扱うことが可能です。記事は、onabortからonwheelまで、様々なイベントの名前と発生条件を詳細な表形式で紹介しています。これにより、Blazor開発者は適切なイベントを状況に応じて選択し、ウェブページのインタラクティビティを高めることができます。

更新日:2023/09/03

カード画像
@keyを使い方

Blazorの@keyディレクティブは、コレクション内の項目を一意に識別し、BlazorがDOMの変更を効率的に行うのを支援します。特にリストや配列の更新時、このディレクティブが不必要なDOM操作を減少させ、アプリのパフォーマンス向上に寄与します。正確な動作のために、指定する要素が一意であることや適切な場所に設定することが重要です。

更新日:2023/09/07

An error has occurred. This application may no longer respond until reloaded. Reload 🗙