次の方法で共有


ASP.NET Core SignalR Swift クライアント

SignalR Swift は、Swift アプリケーションから SignalR サーバーに接続するためのクライアント ライブラリです。 このドキュメントでは、クライアントのインストール、接続の確立、サーバーからクライアントへの呼び出しの処理、サーバー メソッドの呼び出し、ストリーミング応答の操作、自動再接続などのオプションを構成する方法の概要について説明します。

SignalR クライアント パッケージをインストールする

SignalR Swift クライアント ライブラリは、Swift パッケージとして配信されます。 Swift パッケージ マネージャーを使用してプロジェクトに追加できます。

Requirements

  • Swift >= 5.10
  • macOS >= 11.0
  • iOS >= 14

Swift パッケージ マネージャーを使用したインストール

SignalR ファイルに依存関係として Package.swift Swift パッケージを追加します。

// swift-tools-version: 5.10
import PackageDescription

let package = Package(
    name: "signalr-client-app",
    dependencies: [
        .package(url: "https://github.com/dotnet/signalr-client-swift", branch: "main")
    ],
    targets: [
        .executableTarget(name: "YourTargetName", dependencies: [.product(name: "SignalRClient", package: "signalr-client-swift")])
    ]
)

依存関係を追加した後、Swift コードにライブラリをインポートします。

import SignalRClient

ハブに接続する

接続を確立するには、HubConnectionBuilderを作成し、SignalRメソッドを使用してwithUrl() サーバーの URL で構成します。 接続が構築されたら、 start() を呼び出してサーバーに接続します。

import SignalRClient

let connection = HubConnectionBuilder()
    .withUrl(url: "https://your-signalr-server")
    .build()

try await connection.start()

ハブからクライアントのメソッドを呼び出す

サーバーからメッセージを受信するには、 on メソッドを使用してハンドラーを登録します。 on メソッドは、ハブ メソッドの名前と、サーバーがそのメソッドを呼び出したときに実行されるクロージャを受け取ります。

次のメソッド名は ReceiveMessage。 引数の名前は usermessage です。

await connection.on("ReceiveMessage") { (user: String, message: String) in
    print("\(user) says: \(message)")
}

前の connection.on のコードは、サーバー側のコードで SendAsync メソッドを使用してそれが呼び出された時点で実行されます。

using Microsoft.AspNetCore.SignalR;
namespace SignalRChat.Hubs;

public class ChatHub : Hub
{
    public async Task SendMessage(string user, string message)
    {
        await Clients.All.SendAsync("ReceiveMessage", user, message);
    }
}

SignalR により、SendAsyncconnection.on で定義されているメソッド名と引数を突き合わせることで、呼び出すクライアント メソッドが決定されます。

ベスト プラクティスは、try await connection.start()後にHubConnectionon メソッドを呼び出す方法です。 これにより、メッセージを受信する前にハンドラーが確実に登録されます。

クライアントからハブ メソッドを呼び出す

Swift クライアントは、HubConnection の invoke メソッドまたは send メソッドを使用して、サーバー上でハブ メソッドを呼び出すことができます。 invoke メソッドはサーバーの応答を待機し、呼び出しが失敗した場合はエラーをスローしますが、send メソッドは応答を待機しません。

次のコードでは、ハブのメソッド名が SendMessageinvoke に渡される 2 番目と 3 番目の引数は、ハブ メソッドの user および message 引数にマップします。

// Using invoke, which waits for a response
try await connection.invoke(method: "SendMessage", arguments: "myUser", "Hello")

// Using send, which does not wait for a response
try await connection.send(method: "SendMessage", arguments: "myUser", "Hello")

invoke メソッドは、サーバー上のメソッドが戻るときに戻り値 (存在する場合) を返します。 サーバー上のメソッドがエラーを発生させた場合、関数はエラーを発生させます。

ロギング(記録)

Swift クライアント ライブラリには、Swift アプリケーション用に設計された軽量ログ システムが含まれています。 カスタマイズ可能なログ ハンドラーを使用して、さまざまなレベルの重大度でメッセージをログに記録する構造化された方法が提供されます。 Apple プラットフォームでは、効率的なシステム ログ記録のために os.Logger を活用しますが、他のプラットフォームでは標準のコンソール出力にフォールバックします。

ログ レベル

HubConnectionBuilder().withLogLevel(LogLevel:)を使用してログ レベルを設定します。 メッセージは、指定したログ レベル以上でログに記録されます。

  • LogLevel.debug: デバッグに役立つ詳細情報。
  • LogLevel.information: 一般的なアプリケーション メッセージ。
  • LogLevel.warning: 潜在的な問題に関する警告。
  • LogLevel.error: すぐに注意が必要なエラー。

クライアントの結果

サーバー メソッドの呼び出しに加えて、サーバーはクライアントでメソッドを呼び出し、応答を待機できます。 これをサポートするには、クロージャから結果を返すクライアント ハンドラーを定義します。

await connection.on("ClientResult") { (message: String) in
    return "client response"
}

たとえば、サーバーはクライアントで ClientResult メソッドを呼び出し、戻り値を待つことができます。

public class ChatHub : Hub
{
    public async Task TriggerClientResult()
    {
        var message = await Clients.Client(connectionId).InvokeAsync<string>("ClientResult");
    }
}

ストリーミング応答の取り扱い

サーバーからデータストリームを受信するには、 stream メソッドを使用します。 このメソッドは、非同期的に反復処理できるストリームを返します。

let streamResult: any StreamResult<String> = try await connection.stream(method: "StreamMethod")
for try await item in streamResult.stream {
    print("Received item: \(item)")
}

失われた接続を処理する

自動再接続

SignalR Swift クライアントでは、自動再接続がサポートされています。 これを有効にするには、接続の構築中に WithAutomaticReconnect() を呼び出します。 自動再接続は、既定では無効になっています。

let connection = HubConnectionBuilder()
    .withUrl(url: "https://your-signalr-server")
    .withAutomaticReconnect()
    .build()

パラメーターを指定しない場合、withAutomaticReconnect() は、再接続が試行される前に、それぞれ 0、2、10、および 30 秒待機するようにクライアントを構成します。 4 回試行に失敗すると、クライアントは再接続の試行を停止します。

再接続の試行を開始する前に、 HubConnectionReconnecting 状態に遷移し、その onReconnecting コールバックを起動します。

再接続が成功すると、 HubConnectionconnected 状態に遷移し、その onReconnected コールバックを起動します。

onReconnectingonReconnectedを使用する一般的な方法は、接続状態の変化をマークすることです。

connection.onReconnecting { error in
    // connection is disconnected because of error
}

connection.onReconnected {
    // connection is connected back
}

自動再接続の戦略を構成する

再接続の動作をカスタマイズするには、各再接続の試行までの遅延を秒単位で表す数値の配列を渡します。 より詳細な制御を行うために、RetryPolicy プロトコルに準拠するオブジェクトを渡します。

遅延値の配列の使用

let connection = HubConnectionBuilder()
    .withUrl(url: "https://your-signalr-server")
    .withAutomaticReconnect([0, 0, 1]) // Wait 0, 0, and 1 second before each reconnect attempt; stop after 3 attempts.
    .build()

カスタム再試行ポリシーの使用

再試行のタイミングを制御する RetryPolicy プロトコルを実装します。

// Define a custom retry policy
struct CustomRetryPolicy: RetryPolicy {
    func nextRetryInterval(retryContext: RetryContext) -> TimeInterval? {
        // For example, retry every 1 second indefinitely.
        return 1
    }
}

let connection = HubConnectionBuilder()
    .withUrl(url: "https://your-signalr-server")
    .withAutomaticReconnect(CustomRetryPolicy())
    .build()

タイムアウトとキープアライブのオプションを構成する

クライアントのタイムアウトとキープアライブの設定は、HubConnectionBuilder を使用してカスタマイズできます。

オプション デフォルト値 Description
withKeepAliveInterval 15 (秒) クライアントが ping メッセージを送信し、HubConnectionBuilder で直接設定される間隔を決定します。 この設定により、サーバーでハードの切断を検出できます。たとえば、クライアントがコンピューターをネットワークから取り外したときなどです。 クライアントからメッセージを送信すると、タイマーが間隔の開始にリセットされます。 クライアントがサーバー上の ClientTimeoutInterval セットでメッセージを送信していない場合、サーバーはクライアントが切断されたと見なします。
withServerTimeout 30 (秒) クライアントがサーバーからの応答を待機してからサーバーが切断されたと見なす間隔を決定します。 この設定は、HubConnectionBuilder で直接設定されます。

トランスポートの構成

SignalR Swift クライアントでは、LongPolling、ServerSentEvents、WebSocket の 3 つのトランスポートがサポートされています。 既定では、サーバーでサポートされている場合はクライアントは WebSocket を使用し、サポートされていない場合は ServerSentEvents と LongPolling にフォールバックします。 接続の構築中に withUrl(url:transport:) を呼び出すことによって、特定のトランスポートを使用するようにクライアントを構成できます。

let connection = HubConnectionBuilder()
    .withUrl(url: "https://your-signalr-server", transport: .webSockets) // use websocket only
    .build()
let connection = HubConnectionBuilder()
    .withUrl(url: "https://your-signalr-server", transport: [.webSockets, .serverSentEvents]) // use websockets and server sent events
    .build()

その他のリソース