sgcWebSockets を 5 分で
ライブラリのインストールが完了し、パレットが表示されている状態です。このページでは、そこから接続を受け付けるサーバーと、メッセージを送信して応答を読み取るクライアントまでを順に進めます。以下のコードはすべてダウンロードに同梱されているデモから抜粋したものなので、入力する代わりにプロジェクトを開くこともできます。
ライブラリのインストールが完了し、パレットが表示されている状態です。このページでは、そこから接続を受け付けるサーバーと、メッセージを送信して応答を読み取るクライアントまでを順に進めます。以下のコードはすべてダウンロードに同梱されているデモから抜粋したものなので、入力する代わりにプロジェクトを開くこともできます。
非ビジュアルコンポーネント 2 つ、uses 句のユニット 1 つ、そしてイベントハンドラーのパラメーター型のための追加ユニット 1 つです。
TsgcWebSocketClient は sgcWebSocket.pas で宣言され、SGC WebSockets パレットページに登録されています。Host と Port を設定してから Active を設定します。
TsgcWebSocketServer は同じユニット、同じパレットページにあります。Port を設定してから Active を設定します。待ち受けを行い、ハンドシェイクをアップグレードして OnConnect を発生させます。
すべてのイベントは TsgcWSConnection を渡します。これは sgcWebSocket_Classes.pas にあります。デモは uses sgcWebSocket, sgcWebSocket_Classes; と記述しており、同じように記述してください。
どちらのユニットにもプラットフォームガードはなく、両コンポーネントとも ComponentPlatforms(0) で登録されているため、VCL、FMX、コンソール、サービスのいずれのターゲットでもコンパイルできます。FireMonkey クライアントのデモも同梱されています。
エディションの列は、実際にコードを制御する define と、それが Source/sgcVer.inc の何行目にあるかを示しています。
| 項目 | 内容 |
|---|---|
| IDE | Delphi 7 から RAD Studio 13、および C++Builder 2007 から 13。Packages\ 配下に IDE バージョンごとのパッケージグループがあります。 |
| uses 句 | コンポーネントには sgcWebSocket、TsgcWSConnection には sgcWebSocket_Classes を使用します。 |
| クライアントのエディション | TsgcWebSocketClient は {$IFDEF SGC_WS_CLIENT} で囲まれています。SGC_WS_CLIENT は 697 行目、675 行目から 724 行目までの {$IFDEF SGC_EDT_STD} ブロック内で定義されています。つまり Standard 以上です。 |
| サーバーのエディション | TsgcWebSocketServer は直接 {$IFDEF SGC_EDT_PRO} で囲まれており、sgcWebSocket_Reg.pas でのパレット登録も同じガード内にあります。Professional の機能ブロックは 727 行目から 758 行目までです。つまり Professional 以上です。Standard ライセンスで使えるのはクライアントのみで、サーバーは使えません。 |
| パレットページ | 852 行目で定義されている {$IFDEF SGC_PACK_WEBSOCKETS} の下で登録されています。 |
| プラットフォーム | sgcWebSocket.pas、sgcWebSocket_Client.pas、sgcWebSocket_Server.pas にはユニットスコープのプラットフォームガードがありません。Windows では Windows ユニットが条件付きで取り込まれるだけです。 |
お使いのエディションが分からない場合は、Source/sgcVer.inc を開いて最初の 5 行を確認してください。そこにある SGC_EDT_* の define は累積式で、All-Access はすべてを定義し、Standard は最初の 2 つだけを定義します。
zip からコンポーネントを配置できるまでの 5 つの手順です。デザイン時パッケージは実行時パッケージを参照するため、先に実行時パッケージをコンパイルしてください。
ダウンロードしたファイルを任意のフォルダーに展開します。このページ以降では、そのフォルダーを {$DIR} と呼びます。Source\、Packages\、Demos\、lib*\ の各フォルダーはすべてその下にあります。
ツール、オプション、ライブラリの順に開きます。{$DIR}\source と、お使いの IDE に対応するフォルダーを追加します。たとえば RAD Studio 13 では {$DIR}\libD13\$(Platform)、12 では {$DIR}\libD12\$(Platform) です。
お使いの IDE バージョンに合わせて {$DIR}\Packages\sgcWebSocketsD13.groupproj を開きます。最初に sgcWebSocketsD13.dpk をコンパイルし、次に dclsgcWebSocketsD13.dpk をインストールします。C++Builder では同じフォルダーにある .cbproj ファイルを使用します。
SGC WebSockets という新しいページが表示されます。Standard ビルドには TsgcWebSocketClient が含まれます。Professional 以上では、TsgcWebSocketServer、TsgcWebSocketHTTPServer、TsgcWebSocketProxyServer、TsgcWebSocketLoadBalancerServer も含まれます。
何かを書き始める前に、{$DIR}\Demos\01.WebSocket_Quick_Start\01.Server_and_Client_Chat を開いてください。ライブラリで最小の動作するペアであり、以下のコードはここから抜粋したものです。
サーバーを起動し、クライアントを起動して、文字列を送信します。サーバーのタブはポートで待ち受け、クライアントのタブは接続してメッセージを 1 件書き込みます。
uses
Classes, SysUtils,
// sgc
sgcWebSocket, sgcWebSocket_Classes;
procedure TfrmServerChat.btnStartClick(Sender: TObject);
begin
WSServer.Port := 5418;
WSServer.Active := True;
memoLog.Lines.Add('#started');
end;
procedure TfrmServerChat.WSServerConnect(Connection: TsgcWSConnection);
begin
memoLog.Lines.Add('Connected: ' + Connection.IP);
end;
procedure TfrmServerChat.WSServerDisconnect(Connection: TsgcWSConnection;
Code: Integer);
begin
memoLog.Lines.Add('Disconnected (' + IntToStr(Code) + '): ' + Connection.IP);
end;
procedure TfrmServerChat.WSServerMessage(Connection: TsgcWSConnection;
const Text: string);
begin
memoLog.Lines.Add(Text);
// send it straight back, so the client has something to read
Connection.WriteData('echo: ' + Text);
end;
TsgcWebSocketServer をフォームに配置して WSServer という名前を付け、オブジェクトインスペクターから 4 つのハンドラーを IDE に生成させます。Connection.IP と Connection.WriteData はどちらも TsgcWSConnection のメンバーなので、uses 句に sgcWebSocket_Classes が含まれています。
uses
Classes, SysUtils,
// sgc
sgcWebSocket, sgcWebSocket_Classes;
procedure TfrmClientChat.btnStartClick(Sender: TObject);
begin
WSClient.Host := 'localhost';
WSClient.Port := 5418;
WSClient.TLS := False;
WSClient.Active := True;
end;
procedure TfrmClientChat.btnSendClick(Sender: TObject);
begin
if WSClient.Active then
WSClient.WriteData('Hello from Delphi')
else
raise Exception.Create('Not connected');
end;
procedure TfrmClientChat.WSClientConnect(Connection: TsgcWSConnection);
begin
memoLog.Lines.Add('#connected');
end;
procedure TfrmClientChat.WSClientMessage(Connection: TsgcWSConnection;
const Text: string);
begin
memoLog.Lines.Add(Text);
end;
先にサーバープロジェクトを実行し、次にこのプロジェクトを実行します。クライアントのログに #connected が表示され、echo: Hello from Delphi が OnMessage で返ってきます。この往復がクイックスタートのすべてです。
program WSConsoleClient;
{$APPTYPE CONSOLE}
uses
Classes, SysUtils,
// sgc
sgcWebSocket, sgcWebSocket_Classes;
type
TChatHandler = class
procedure DoConnect(Connection: TsgcWSConnection);
procedure DoMessage(Connection: TsgcWSConnection; const Text: string);
end;
procedure TChatHandler.DoConnect(Connection: TsgcWSConnection);
begin
Writeln('#connected');
end;
procedure TChatHandler.DoMessage(Connection: TsgcWSConnection;
const Text: string);
begin
Writeln('Server says: ', Text);
end;
var
oClient: TsgcWebSocketClient;
oHandler: TChatHandler;
begin
oHandler := TChatHandler.Create;
oClient := TsgcWebSocketClient.Create(nil);
try
oClient.Host := 'localhost';
oClient.Port := 5418;
oClient.WatchDog.Enabled := True; // reconnect on its own
// assign the handlers BEFORE Active, or the first
// OnConnect can fire with nothing attached
oClient.OnConnect := oHandler.DoConnect;
oClient.OnMessage := oHandler.DoMessage;
oClient.Active := True;
oClient.WriteData('Hello from Delphi');
Readln;
finally
oClient.Free;
oHandler.Free;
end;
end.
クライアントは独自のスレッドで動作するため、コンソールプログラムではメインスレッドを維持し続ける必要があります。そのために Readln を使っています。
サーバーとクライアントのタブは、同梱のデモ Demos\01.WebSocket_Quick_Start\01.Server_and_Client_Chat から、デモ固有のチェックボックスや入力ボックスの処理を取り除いたものです。3 つ目のタブは、フォームに配置する代わりに実行時に作成したコンポーネントに対して、同じ呼び出しを記述したものです。
最初の実行については 4 つのイベントで全体が分かります。先に進む前に、4 つすべてを接続しておきましょう。
Activeサーバーでは、Active := True は成功するか例外を発生させます。ポートが使用中であれば、数手順先ではなくここで分かります。
OnConnectprocedure(Connection: TsgcWSConnection)。両側で発生します。サーバーでは Connection.IP で接続してきた相手が分かり、クライアントではハンドシェイクがアップグレードされた証拠になります。
OnMessageprocedure(Connection: TsgcWSConnection; const Text: string)。クライアントにエコーが返ってくれば、往復通信がエンドツーエンドで確認できたことになります。
OnError と OnExceptionprocedure(Connection: TsgcWSConnection; const Error: string) と procedure(Connection: TsgcWSConnection; E: Exception)。両方とも接続してください。これらがないと、障害が通知されず、何も起きていないように見えます。
初回実行時の問題のほとんどは、次の 6 つのいずれかです。
TsgcWebSocketServer がパレットにないサーバークラスは SGC_EDT_PRO が定義されている場合のみ、sgcWebSocket.pas の 130 行目でコンパイルされ、同じガード内でのみ登録されます。Standard ビルドではクライアントはありますが、サーバーはありません。これはライセンスによるもので、インストールの不具合ではありません。
TsgcWSConnectionコンポーネントは sgcWebSocket に、接続オブジェクトは sgcWebSocket_Classes にあります。2 つ目のユニットを uses 句に追加してください。同梱のデモにはすべて両方が含まれています。
WatchDog.Enabled := True を設定して、切断された接続が自動的に再接続されるようにし、OnError と OnException を処理してください。ハンドラーがない状態での無通知の切断は、何も起きていないように見えます。
書き込む前に、クライアントが実際に接続されていることを確認してください。非アクティブなクライアントに対する WriteData は何の効果もありません。デモが送信前に if WSClient.Active then を確認しているのはそのためです。
サーバーの別のインスタンスや別のプログラムが、まだそのポートを使用しています。それを停止するか、サーバーを空いているポートに変更してください。デモの既定値は 5416 と 5418 です。
wss:// 接続には、動作する TLS バックエンドが必要です。TLSOptions.IOHandler で選択します。OpenSSL はどこでも使え、SChannel は Windows で DLL の配布が不要で、Apple と Android のネイティブハンドラーは Enterprise エディションで利用できます。
チャットのペアは出発点にすぎません。作業が向かいやすい 4 つの方向を示します。いずれも同じライブラリに含まれています。
同じクライアントで、MQTT、AMQP、STOMP、Kafka、WAMP のサブプロトコルコンポーネントを利用できます。いずれかを配置し、その Client プロパティを TsgcWebSocketClient に向ければ、ブローカーに接続できます。
TsgcWebSocketHTTPServer は、通常の HTTP リクエストと WebSocket のアップグレードを同じポートで処理します。ブラウザーがソケットを開く前にページを取得する必要がある場合に適しています。
Enterprise エディションでは、クラスタリング、ロードバランサーサーバー、プロキシサーバーが追加され、1 つの論理エンドポイントを複数のサーバープロセスの前段に置けます。
レート制限、サーキットブレーカー、API キーマネージャー、ファイアウォールの各コンポーネントは、既存のサーバーにそのまま追加できます。
リファレンスページには、すべてのプロパティとイベントが記載されています。デモプロジェクトはダウンロードに含まれており、Demos\01.WebSocket_Quick_Start の下にあります。
リファレンス、WebSocket クライアント
TsgcWebSocketClient のすべてのプロパティ、メソッド、イベント。
|
開く | |
リファレンス、WebSocket サーバー
TsgcWebSocketServer のバインド、認証、ブロードキャスト、接続管理。
|
開く | |
| オンラインヘルプ、TsgcWebSocketClient 自動生成されたコンポーネントリファレンスで、常に最新リリースに対応しています。 | 開く | |
| 必要なエディションは Standard、Professional、Enterprise、All-Access がそれぞれ有効にする機能を、機能ごとに説明します。 | 開く | |
| 体験版のダウンロード 製品版と同じインストーラーで、期間限定、IDE バージョンごとに 1 つです。 | 開く | |
| ユーザーマニュアル (PDF) ライブラリ内のすべてのコンポーネントを網羅した完全なマニュアルです。 | 開く |
関連資料:WebSocket とは何か、クライアントの接続と WatchDog のイベント、WebSocket サーバーのセキュリティ。各製品にはそれぞれクイックスタートがあり、はじめにのページに一覧があります。
sgcWebSocket で TsgcWebSocketClient と TsgcWebSocketServer が使えます。すべてのイベントは TsgcWSConnection を渡し、その型は sgcWebSocket_Classes で宣言されているため、こちらも追加してください。同梱のデモは uses sgcWebSocket, sgcWebSocket_Classes; と記述しており、サーバーのデモではさらに sgcWebSocket_Server を追加しています。
{$IFDEF SGC_EDT_PRO} の内側でコンパイルされ、sgcWebSocket_Reg.pas でのパレット登録も同じガード内にあります。SGC_EDT_PRO は、sgcVer.inc の 727 行目から 758 行目にある Professional の機能ブロックを有効にします。Standard ビルドではクライアントのみがコンパイルされます。クライアントの define である SGC_WS_CLIENT は、675 行目から 724 行目の Standard ブロック内の 697 行目にあります。
sgcWebSocket_Classes.pas に由来します。OnConnect は procedure(Connection: TsgcWSConnection)、OnDisconnect は procedure(Connection: TsgcWSConnection; Code: Integer)、OnMessage は procedure(Connection: TsgcWSConnection; const Text: string)、OnError は procedure(Connection: TsgcWSConnection; const Error: string)、OnException は procedure(Connection: TsgcWSConnection; E: Exception) です。パラメーターの過不足は最初のプロジェクトで最もよくあるコンパイルエラーなので、手入力せずに IDE に生成させてください。
sgcWebSocket.pas、sgcWebSocket_Client.pas、sgcWebSocket_Server.pas にはユニットスコープのプラットフォームガードがなく、両コンポーネントとも ComponentPlatforms(0) で登録されているため、IDE がターゲットを制限することはありません。FireMonkey のクライアントとサーバーのデモは Demos\01.WebSocket_Quick_Start\07.Firemonkey_Server_and_Client に同梱されています。ライブラリ内でプラットフォームが制限されている WebSocket コンポーネントは TsgcWebSocketClient_WinHTTP だけで、Win32 と Win64 に対応しています。
TLS := True を設定し、Port を TLS ポートに向けます。次に TLSOptions.IOHandler で TLS バックエンドを選択します。OpenSSL はどこでも動作し、Windows では実行ファイルと同じ場所に libcrypto-3.dll と libssl-3.dll が必要です。SChannel は Windows 専用で、追加ファイルは不要です。Apple と Android のネイティブハンドラーは Enterprise の機能です。
Active := True を設定する前にイベントハンドラーを割り当ててください。そうしないと、ハンドラーが接続される前に最初の OnConnect が発生することがあります。コンソールアプリケーションでは、クライアントが独自のスレッドで動作するためメインスレッドを維持し続ける必要があり、サンプルが Readln で終わっているのはそのためです。
WatchDog.Enabled := True を設定し、既定値が積極的すぎる場合は WatchDog.Interval と WatchDog.Attempts を調整してください。
Demos\ の下にあります。このページで使用しているペアは 01.WebSocket_Quick_Start\01.Server_and_Client_Chat です。早めに開いておきたいものとして、資格情報を確認するサーバーの 06.Authentication、クロスプラットフォームクライアントの 07.Firemonkey_Server_and_Client、接続のサブセットへのブロードキャストの 12.Groups もあります。