GeneXus Evoution 3 の Web 機能を使用することで、Facebook のウォールとよく似た Web ページを実装できます。このページでは、特定のトピックに関するユーザーのコメントが表示され、ユーザーが新しいコメントを追加可能で、その更新内容をリアルタイムで表示できます。
ユーザーが投稿に対して新しいコメントを追加 (またはウォールに投稿を追加) した場合、次の条件が満たされる必要があります:
- 同じページを参照しているほかのユーザーが、Web ページを再表示することなく、自身の画面上で新しいコメントを受信する。
- 別のユーザーが新しいコメントを同時に編集中だった場合、入力中の内容を失うことなく、1 人目のユーザーのコメントを受信する。
この条件を満たすには、次の機能を実装する必要があります:
- Server.Socket 外部オブジェクトを使用することで、クライアントからサーバーに要求を送ることなく、クライアントに通知が送信されるようにします。
- [ Web User Experience ] プロパティを Smooth に設定することで、ユーザー定義イベントを実行するたびにオブジェクトのローカルで再表示が行われ、ページ全体の再表示は行われないようにします。
- 技術的には、単一のグリッド行の再表示を実現できる必要があります。この場合、GeneXus X Evolution 3 におけるクライアント側でのイベント実行およびユーザーイベントの Load コマンドと Load メソッドのメリットを活用できます。
このような内容は、後述の設計とサンプルコードを使用して実現できます。
次のような簡略化された構造があるとします:
図 1.
フォーラムメッセージを表示する Web パネルは "MessagingSample" という名前であり、次のエレメントが含まれます:
- &newComment 文字列変数と、新しい投稿を追加するための "Comment" ボタン。
- Web コンポーネントをロードする、"PostComment" という名前のフリー スタイル グリッド。このフリー スタイル グリッドには、行の識別子が格納される &PostId 変数も含まれています。
図 2.
図に示しているように、このフリー スタイル グリッドをロードするコードは次のとおりです:
Event Load
for each //"post" テーブルでループし、Web コンポーネント内の投稿とコメントをロード
WEbComp1.Object = PostComment.Create(PostId)
WEbComp1.Visible=true
&postid=PostId //&PostId はフリースタイルに含まれる変数
load
endfor
Endevent
"Comment" ボタンは "Comment" イベントに関連付けられており、このイベントのコードは次のとおりです:
Event 'comment'
InsertNewpost.Call(&newcomment)
Endevent
insertNewpost プロシージャーについては以降で説明します。
'PostComment' Web コンポーネントには、投稿とそのコメントをロードするフリー スタイル グリッドがあります。
図 3.
"PostComment" ボタンは 'Postcomment' イベントに関連付けられており、ここでユーザーはこの投稿に新しいコメントを追加できます。
PostComment イベントのコードは次のとおりです:
Event 'Postcomment'
InsertNewComment.Call(PostId, &newcomment)
&newcomment=""
Grid1.Refresh()
Endevent
'PostComment' イベント内の Grid1.Refresh() コマンドに注目してください。このコマンドは、グリッドに新しいコメントが追加された後に、ページ全体とそのコンテナは再表示せずに、グリッドを再表示します。これは、[ Web User Experience ] プロパティが Smooth に設定されているために実現されます。
'InsertNewComment' プロシージャーによって、コメントがデータベース内に挿入され、その後、通知を送信するプロシージャーが呼び出されます。プロシージャーの呼び出しは次のようになり、ここで &PostId をパラメーターとして渡しています:
call(NewCommentNotification, &PostId)
NewCommentNotification プロシージャーは、Server.Socket 外部オブジェクトを使用してブロードキャスト通知を送信する必要があります。コードは次のようになります:
parm(in:&PostId);
&NotificationInfo.Id=&PostId.ToString() //&NotificationInfo は NotificationInfo データタイプPostId を NotificationInfo Id フィールドに格納します。
&NotificationInfo.Message='Comment’
&webnotification.Broadcast(&NotificationInfo)
このコードが実行されるときに、すべてのクライアントに対する通知が、WebSocket を使用して自動的にトリガーされます。
特に、前述のコードで使用されている InsertNewpost プロシージャーは InsertNewComment と似ています。これは、新しい投稿をデータベースに挿入し、新しい投稿の通知を送信するプロシージャーを呼び出します。新しい投稿の通知を送信するプロシージャーは次のようになります:
&NotificationInfo.Id=&PostId.ToString() //&NotificationInfo は NotificationInfo データタイプPostId を NotificationInfo Id フィールドに格納します。
&NotificationInfo.Message='Post’
&webnotification.Broadcast(&NotificationInfo)
クライアント Web パネルに OnMessage イベントがプログラミングされていれば、この通知が検知され、結果としてアクションが実行されます。
この例では、新しいコメントの通知が到着するたびにグリッド行を自動的に再表示する必要があります。
そのため、"MessagingSample" パネルは次のようにプログラミングされます:
Event OnMessage(&NotificationInfo)
if &NotificationInfo.Message = "Comment"
for each line
if (&NotificationInfo.Id=&postid.ToString())
WebComp1.refresh()
endif
endfor
else
&postid = ¬ificationInfo.Id.Trim().ToNumeric()
webcomp1.Object = PostComment.Create(&PostId)
load
endif
Endevent
&postId 変数は、グリッド行内のフォーム上にあります。
ここで重要なのは、WebComp1.refresh() イベントは、受け取った通知の PostId と対応する投稿をロードするグリッド行に対してのみ実行されることです。この行だけが再表示されるため、通知を受け取ったときにユーザーが編集中だった場合も、その内容が失われることがありません。For Each line コマンドは、クライアント側で実行されます。「GeneXus X Evolution 3 におけるクライアント側でのイベント実行」を参照してください。
ユーザーイベントの Load コマンドと Load メソッドの説明にあるように、ロードイベントによって、グリッドを再表示することなく新しい行が追加されます。
サンプルはここからダウンロードできます。
Web 通知およびプログレス ユーザー コントロールの要件
|