4D 20 R8 では、TCPConnectionクラスを導入し、リモートサーバーへの TCP接続を開始できるようになりました。4D v20 R9 では、TCPListenerクラスが導入され、4D で直接 TCP接続の着信を処理し、TCPサーバーを構築できるようになりました。
TCPConnection と TCPListenerクラスがあれば、クライアント側とサーバー側の両方で、TCP通信を完全にコントロールすることができます。
この 2つのクラスの使い方を説明します。
この記事を読み進める前に、TCPConnectionクラスに関する以前のブログ記事をチェックし、基礎を理解することを強くお勧めします。

TCPListenerクラスと TCPConnectionクラスの関係図
接続クラスの定義
前の例で使用した ConnectionToTheServerクラスをモデルにして、ServerSideConnection という新しいクラスを作成します。実装する主なコールバックの内訳は以下のとおりです:
Class constructor()
// 接続に成功したときに呼び出されるコールバック
Function onConnection($connection : 4D.TCPConnection; $event : 4D.TCPEvent)
ALERT("接続しました")
// 接続が正常に解除されたときに呼び出されるコールバック
Function onShutdown($connection : 4D.TCPConnection; $event : 4D.TCPEvent)
ALERT("接続が解除されました")
// データを受信したときに呼び出されるコールバック。この簡単なサーバーは常に、ユーザーに表示するテキストを返信します
Function onData($connection : 4D.TCPConnection; $event : 4D.TCPEvent)
ALERT(BLOB to text($event.data; UTF8 text without length))
// 接続が予定外に解除されたときに呼び出されるコールバック
Function onError($connection : 4D.TCPConnection; $event : 4D.TCPEvent)
ALERT("接続エラー")
このクラスは、主要な TCPイベントに反応する単純なシェルです。
リスナークラスの設定
次は、特定のポートで待ち受け、接続の着信を受け付ける ServerListenerクラスを作成しましょう:
property listener:4D.TCPListener
shared singleton Class constructor()
// 引数で指定したポートをリッスンする TCPListener を作成します
shared Function startListening($port:integer)
This.listener:=4D.TCPListener.new($port, This)
// リスナーを停止します
shared Function stopListening()
This.listener.terminate()
// 接続を受信すると呼び出されるコールバック
Function onConnection($listener : 4D.TCPListener; $event : 4D.TCPEvent)->$result
ALERT("Listener: onConnection")
if ($event.IP = "a good IP address")
$result:=cs.ServerSideConnection.new()
else
$result := null
end if
// すでに別のアプリケーションによって使用されているなど、エラーによりポートをリッスンできない場合に呼び出されるコールバック
Function onError($listener : 4D.TCPListener; $event : 4D.TCPEvent)
ALERT("Listener: onError")
リスナーを開始するには:
cs.ServerListener.me.startListening($port)
クライアントが接続を試みるたびに、onConnection関数がトリガーされます。接続を受け入れる場合はServerSideConnectionオブジェクトを返し、拒否する場合は NULL を返します。いったん接続が許可されると、対応するTCPConnectionコールバックが開始され、他のクライアントと同じように接続を処理することができます。
新規接続のリッスンを停止するには:
cs.ServerListener.me.stopListening()
注記: アクティブな接続は、手動で閉じるまで残ります。
統一されたクラス構造 = 簡素化されたコード
この設計の主な利点は、クライアント接続とサーバー接続の両方に同じ TCPConnectionクラスが使われることです。この対称性により、実装が単純化され、コードの再利用が促進されます。
まとめ
4D v20 R9 に TCPListenerクラスが追加されたことで、4D で堅牢な TCPサーバーを作成できるようになりました。TCPConnection と組み合わせることで、新しいツールは、双方向の TCP通信を扱うための完全なフレームワークを提供します。
質問やフィードバックがあれば、遠慮なく4Dフォーラムにお寄せください。
