プッシュメッセージの送信

Cloud Code C# モジュールでは、WebSocket を介してメッセージをクライアントにプッシュできます。このページでは、この機能の概要と、Cloud Code モジュールおよび Cloud Code SDK で使用する方法について説明します。

ノート: プッシュメッセージと プッシュ通知 は、ゲーム内で異なる目的を果たします。プッシュメッセージはゲームプレイをアクティブに行っているプレイヤーをターゲットとし、ゲームが非アクティブであるかバックグラウンドで動作している場合にはプッシュ通知がデバイスに届きます。

プッシュメッセージを送信するには、モジュールエンドポイントを呼び出す必要があります。Unity エディターからプッシュメッセージをサブスクライブできます。

ユースケースと利点

プッシュメッセージは、以下のようなさまざまな目的に使用できます。

用途利点
サーバーからクライアントにリアルタイムでメッセージをプッシュし、ゲームのインタラクティビティを強化します。ゲームイベント、更新、非同期マルチプレイヤーゲーム (例えば、競争型カードゲームなど) についてプレイヤーに通知できます。リアルタイムインタラクション
更新と通知をクライアントに直接プッシュすることにより、ゲーム内の最新のイベント、変更、またはアクションでユーザーを最新に保ちます。新しいデータが使用可能になるとすぐにユーザーに通知できるため、手動でリフレッシュしたり、更新を確認したりする必要がありません。これは、リアルタイムストラテジーゲームなど、頻繁な更新が必要なゲームで特に役立つ可能性があります。ユーザー体験
WebSocket を使用して、従来のポーリング手法よりも効率よくメッセージをプッシュします。クライアントは、新しいデータについて継続的にサーバーに尋ねるかわりに、新しいデータが使用可能になったときに、サーバーがそれを送信するのを待つことができます。これにより、不必要なネットワークトラフィックが削減され、待ち時間の短縮につながる可能性があります。効率的なネットワーク使用状況
プッシュモデルのスケーラビリティを使用して、ユーザー数の多いゲームをサポートします。Cloud Code でプッシュメッセージを使用して、接続されているすべてのクライアントに更新を一度に送信し、プレイヤー数の多いマルチプレイヤーゲームの運用コストとリクエストの量を削減できます。スケーラビリティとコスト
イベント主導モデルでさまざまなタイプのメッセージへのゲームのレスポンスをカスタマイズします。受信したメッセージの MessageType プロパティに基づいて異なるゲームアクションをトリガーできます。カスタマイズ可能性
Unity エコシステムの一部として、Cloud Code の使用は他の Unity サービスとシームレスに行われます。Unity の Authentication サービスでプレイヤー認証を処理し、Unity ゲームエンジン内でメッセージを処理できます。シームレスなインテグレーション

モジュールの作成

以下のコード例は、2 つのメソッドを含むモジュールの基本構造を示します。

  • SendPlayerMessage: 特定の接続済みプレイヤーにメッセージを送信します。
  • SendProjectMessage: プロジェクト内のすべての接続済みプレイヤーにメッセージをブロードキャストします。

Unity.Services.CloudCode.Apis パッケージは、PushClient インスタンスを提供します。これは、プッシュメッセージの送信に使用するインターフェースです。

C#

using Microsoft.Extensions.DependencyInjection;
using Unity.Services.CloudCode.Core;
using Unity.Services.CloudCode.Apis;

namespace PushExample
{
    public class PushExample
    {
        [CloudCodeFunction("SendPlayerMessage")]
        public async Task<string> SendPlayerMessage(IExecutionContext context, PushClient pushClient, string message, string messageType, string playerId)
        {
            var response = await pushClient.SendPlayerMessageAsync(context, message, messageType, playerId);
            return "Player message sent";
        }

        [CloudCodeFunction("SendProjectMessage")]
        public async Task<string> SendProjectMessage(IExecutionContext context, PushClient pushClient, string message, string messageType)
        {
            var response = await pushClient.SendProjectMessageAsync(context, message, messageType);
            return "Project message sent";
        }
    }

    public class ModuleConfig : ICloudCodeSetup
    {
        public void Setup(ICloudCodeConfig config)
        {
            config.Dependencies.AddSingleton(PushClient.Create());
        }
    }
}

モジュールのデプロイ方法を学習するには、Hello World のデプロイ ページを参照してください。

Unity エディターの設定

Cloud Code SDK は、メッセージをサブスクライブするためのインターフェースを提供します。特定のプレイヤーまたはプロジェクト全体のメッセージをサブスクライブできます。

Unity エディターで Cloud Code を使用するには、最初に Cloud Code SDK をインストールし、Unity Gaming Services プロジェクト を Unity エディターにリンクする必要があります。

プロジェクトのリンク

Unity Gaming Services プロジェクト を Unity エディターにリンクします。UGS プロジェクト ID は Unity Dashboard にあります。

  1. Unity エディターで、Edit (編集) > Project Settings (プロジェクト設定) > Services (サービス) の順に選択します。

  2. プロジェクトをリンクします。
    プロジェクトに Unity プロジェクト ID がない場合:

    1. Create a Unity Project ID (Unity プロジェクト ID の作成) > Organizations (組織) の順に選択し、ドロップダウンから組織を選択します。
    2. Create project ID (プロジェクト ID を作成) を選択します。


    既存の Unity プロジェクト ID がある場合:

    1. Use an existing Unity project ID (既存の Unity プロジェクト ID を使用) を選択します。
    2. ドロップダウンから組織とプロジェクトを選択します。
    3. Link project ID (プロジェクト ID をリンク) を選択します。

これにより、Unity プロジェクト ID が表示され、プロジェクトが Unity サービスにリンクされます。また、UnityEditor.CloudProjectSettings.projectId パラメーターを使用して Unity エディタースクリプトのプロジェクト ID にアクセスすることもできます。

SDK のインストール

Unity エディターの最新の Cloud Code パッケージをインストールします。

  1. Unity エディターで、Window (ウィンドウ) > Package Manager (パッケージマネージャー) を開きます。
  2. Package Manager で、Unity Registry (Unity レジストリ) のリストビューを選択します。
  3. com.unity.services.cloudcode を検索するか、リストから Cloud Code パッケージを探します。
  4. このパッケージを選択し、Install (インストール) をクリックします。

ノート: Cloud Code SDK バージョン 2.4.0 以上でメッセージをサブスクライブできます。

ノート: Unity Package Manager インターフェースについて理解するには、Package Manager ウィンドウ のドキュメントを参照してください。

SDK の設定

Cloud Code SDK の使用を準備します。

  1. Cloud Code サービスダッシュボードページを介してサービスが有効になっていることを確認します。
  2. Cloud Code と Authentication SDK の両方をインストールしたことを確認します。
  3. Edit (編集) > Project Settings (プロジェクト設定) > Services (サービス) を選択して、Unity エディター内からクラウドプロジェクトにサインインします。
  4. Unity エディターで新しい C# Monobehaviour スクリプトを作成します。Unity マニュアルの スクリプトの作成と使用 を参照してください。
  5. スクリプトで、await UnityServices.InitializeAsync() を使用して Core SDK を初期化します。
  6. スクリプトで、Authentication SDK を初期化します。

ノート: プレイヤーが Cloud Code サービスにアクセスするには有効なプレイヤー ID とアクセストークンが必要です。いずれかの Cloud Code API を使用する前にプレイヤーを Authentication SDK で認証する必要があります。これを匿名認証用の以下のコードスニペットで行うか、詳細および他のサインイン方法について Authentication のドキュメントを確認できます。

C#

await AuthenticationService.Instance.SignInAnonymouslyAsync();

メッセージのサブスクライブ

特定のプレイヤーまたはプロジェクト全体のメッセージをサブスクライブできます。以下のコードスニペットを、Unity プロジェクトの MonoBehaviour スクリプトのガイドとして使用できます。

スクリプトは匿名プレイヤーとして認証され、プレイヤー固有とプロジェクト固有の両方のメッセージをサブスクライブし、さまざまなタイプのイベントを処理します。

C#

using System;
using System.Threading.Tasks;
using Newtonsoft.Json;
using Unity.Services.Authentication;
using Unity.Services.CloudCode;
using Unity.Services.CloudCode.Subscriptions;
using Unity.Services.Core;
using UnityEngine;
namespace CloudCode
{
	public class CloudCodePushExample : MonoBehaviour
	{
    	async void Start()
        {
            await UnityServices.InitializeAsync();
            await AuthenticationService.Instance.SignInAnonymouslyAsync();
            Debug.Log(AuthenticationService.Instance.PlayerId);
            await SubscribeToPlayerMessages();
            await SubscribeToProjectMessages();
        }
        // This method creates a subscription to player messages and logs out the messages received,
        // the state changes of the connection, when the player is kicked and when an error occurs.
        Task SubscribeToPlayerMessages()
        {
            // Register callbacks, which are triggered when a player message is received
            var callbacks = new SubscriptionEventCallbacks();
            callbacks.MessageReceived += @event =>
            {
                Debug.Log(DateTime.Now.ToString("yyyy-MM-dd'T'HH:mm:ss.fffK"));
                Debug.Log($"Got player subscription Message: {JsonConvert.SerializeObject(@event, Formatting.Indented)}");
            };
            callbacks.ConnectionStateChanged += @event =>
            {
                Debug.Log($"Got player subscription ConnectionStateChanged: {JsonConvert.SerializeObject(@event, Formatting.Indented)}");
            };
            callbacks.Kicked += () =>
            {
                Debug.Log($"Got player subscription Kicked");
            };
            callbacks.Error += @event =>
            {
                Debug.Log($"Got player subscription Error: {JsonConvert.SerializeObject(@event, Formatting.Indented)}");
            };
            return CloudCodeService.Instance.SubscribeToPlayerMessagesAsync(callbacks);
        }
        // This method creates a subscription to project messages and logs out the messages received,
        // the state changes of the connection, when the player is kicked and when an error occurs.
        Task SubscribeToProjectMessages()
        {
            var callbacks = new SubscriptionEventCallbacks();
            callbacks.MessageReceived += @event =>
            {
                Debug.Log(DateTime.Now.ToString("yyyy-MM-dd'T'HH:mm:ss.fffK"));
                Debug.Log($"Got project subscription Message: {JsonConvert.SerializeObject(@event, Formatting.Indented)}");
            };
            callbacks.ConnectionStateChanged += @event =>
            {
                Debug.Log($"Got project subscription ConnectionStateChanged: {JsonConvert.SerializeObject(@event, Formatting.Indented)}");
            };
            callbacks.Kicked += () =>
            {
                Debug.Log($"Got project subscription Kicked");
            };
            callbacks.Error += @event =>
            {
                Debug.Log($"Got project subscription Error: {JsonConvert.SerializeObject(@event, Formatting.Indented)}");
            };
            return CloudCodeService.Instance.SubscribeToProjectMessagesAsync(callbacks);
        }
	}
}

プレイヤーへのメッセージの送信

プレイヤーにメッセージを送信するには、モジュールから SendPlayerMessage または SendProjectMessage 関数を呼び出します。

モジュールを実行する方法については、モジュールの実行 を参照してください。

Unity Runtime からの実行

CloudCodeService インスタンスの CallModuleEndpointAsync メソッドを介して他のプレイヤーにメッセージを送信できます。モジュール名と関数名を最初の 2 つの引数として使用し、ディクショナリと必要なパラメーターを 3 番目の引数として使用する必要があります。

例えば、プレイヤーにメッセージを送信するには、以下を呼び出します。

var sendPlayerMessageResult = await CloudCodeService.Instance.CallModuleEndpointAsync<string>("PushExample", "SendPlayerMessage",
	new Dictionary<string, object> {{"message", "hello with a player message from PushExample!"}, {"messageType", "testType"}, {"playerId", "<other-unity-player-ID>"}});

ノート: このユースケースでは、アクセス制御 ポリシーを作成して、プレイヤーのエンドポイントへのアクセスを制限できます。例えば、プレイヤーが、ゲーム内の他のすべてのプレイヤーにプロジェクトメッセージを送信する SendProjectMessage モジュール関数を呼び出せないようにすることができます。

イベント

プレイヤー固有とプロジェクト固有の両方のサブスクリプションには、4 つのイベントハンドラーがあります。

  • MessageReceived: プレイヤーが新しいメッセージを受信したときにトリガーします。
  • ConnectionStateChanged: 接続の状態が変わったときにトリガーします。
  • Kicked: サーバーがプレイヤーのメッセージのサブスクライブを強制的に解除したときにトリガーします。これにより WebSocket 接続はクローズされず、ゲームクライアントがメッセージを再びサブスクライブすることも阻止されません。
  • Error: 接続の処理時またはプレイヤーがメッセージを受信したときにトリガーします。

メッセージエンベロープ

IMessageReceivedEvent は、プレイヤーがプッシュサービスから受信するメッセージを表すインターフェースです。イベントは、Cloud Code が WebSocket 接続を介してメッセージを送信したときにトリガーします。

IMessageReceivedEvent インターフェースのペイロードについては、以下の表を参照してください。

プロパティ説明
SpecVersion受信したメッセージのエンベロープの仕様バージョン。このプロパティを使用して、クライアントがメッセージを正しく処理できることを確認します。1.0
Idメッセージの一意の識別子。このプロパティを使用して、メッセージを追跡またはログに記録します。4f88f657-27da-4b1d-a013-9033dbc7b48b
Sourceメッセージのエンベロープのソース。これは、メッセージが発生した場所を示し、メッセージのデバッグまたはルーティングに使用できます。ソースは常に Cloud Code のドメインです。https://cloud-code.service.api.unity.com
Typeメッセージのエンベロープタイプ。このプロパティは、メッセージに含まれるデータのタイプを示し、クライアントがその処理方法を決定するのに役立ちます。値は常に Cloud Code メッセージタイプです。com.unity.services.cloud-code.push.v1
Timeメッセージ作成の日付と時間。このプロパティを使用して、メッセージをログに記録したり、待ち時間を計算したりできます。2023-09-19T10:26:40.436878688Z
ProjectIdメッセージが関連付けられているプロジェクトの ID。b6670776-9fd3-4d66-8bf4-63fb1112dc95
EnvironmentIdメッセージが対象としている環境の ID。このプロパティを使用して、開発、ステージング、運用などのさまざまな環境を区別できます。a4bc2571-d1e7-4507-9cc9-80b687d48d8f
CorrelationId関連メッセージの順序を追跡するために使用できる識別子。例えば、複数のメッセージが会話またはワークフローを形成する場合、それらは相関 ID を共有します。afbd7c6e-e999-4ca2-86fc-3c908ba83bf2
MessageCloud Code からプレイヤーに送信された実際のメッセージコンテンツ。"hello world!"
MessageTypeプレイヤーが受信するメッセージのタイプ。これは Type と同様ですが、エンベロープではなくメッセージのコンテンツに固有です。"Information"

ネットワークの使用量とコストの考慮事項

Cloud Code WebSocket 機能を使用してクライアントにメッセージをプッシュする場合、ネットワークの使用量と関連するコストについて重要な考慮事項があります。

エグレスコスト

モジュールからクライアントに送信する各メッセージはネットワーク帯域幅を消費し、モジュールからのアウトバウンドデータの合計量に影響します。Cloud Code は、WebSocket 接続上でのメッセージのプッシュに関連するネットワーク使用量を Cloud Code エグレスコストに追加します。

アプリケーションを設計する際にはこのことを念頭に置き、メッセージを送信するタイミングと頻度を決定することが重要です。過剰または不必要に大きいメッセージは、エグレスコストが高くなる原因となります。

Cloud Code 価格設定の詳細については、コスト のページを参照してください。

メッセージサイズの制限

Cloud Code は、WebSocket 接続に送信されるメッセージのサイズを 10 KB に制限します。これは、より複雑またはデータの多いアプリケーションでは特に、送信するデータのサイズを管理する必要があることを意味します。

以下の方法を使用して、プレイヤーに常に最新情報を伝え、コストとネットワーク使用量を低く保つこともできます。

データの差分の送信

大量のデータまたはゲーム状態の大幅な変化を伝える必要がある場合は、ペイロード全体ではなくデータの差分を送信できます。差分は、既存の状態に適用する変更のセットであり、多くの場合に完全な状態データよりもはるかに小さくなります。

データの HTTP リクエストのプロンプト表示

WebSocket メッセージをナッジメカニズムとして使用して、新しいデータが使用可能であることをクライアントに通知し、完全なデータセットを取得するには HTTP リクエストを行うよう求めるプロンプトを表示できます。この方法は、完全なデータセットが大きく、頻繁ではない更新のみが必要な場合、または HTTP を介してデータを取得する方が効率的またはコスト効果が高い場合に使用できます。