Same page different params!

View: New views
4 Messages — Rating Filter:   Alert me  

Same page different params!

by stojadinovicp :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message



Hi everyone!

In short, the problem is the following. Its an online card game with Rooms and Tables organization. Now, one JSP is used to open different rooms, naturally. Same goes for tables. Depending on the params passed, like "room/index.jsp?roomID=NewOrleans" for example, and then another room "room/index.jsp?roomID=BabyBlue"

The problem is that when I use:
        String currentPage = wctx.getCurrentPage();
        Collection<ScriptSession> sessions = wctx.getScriptSessionsByPage(currentPage);
        for (ScriptSession ss : sessions) ss.addScript(new ScriptBuffer(js));

then ALL rooms get ALL messages :(((
So, if a user chats in one room, this goes to all the rooms :(((

It does make sense to see "room/index.jsp" as one page regardless of the "?roomID=BlaBla" part, but therein lies my problem :(

Now, one obvious solution is to include the roomID in the JavaScript call and then if the roomID is not valid I ignore the message. BUT, this sucks big time because the idea is to have a few rooms but each of these should have many tables opened at the same time. So there will be a LOT of messages flying around and being ignored. In other words, one table page will get ALL messages from ALL tables in ALL rooms.

I would REALLY like to avoid sending THIS much data to my users :(

Any ideas how to solve this? PLEASE!
ANY idea is welcome! And I do have a deadline :(((

THANKS!!!

Re: Same page different params!

by Cameron Braid :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

Here's a rough class (typed in my mail program and therefore not compiled, let alone tested) that could do this for you.

There is room for improvement on many fronts, but it gives the basic idea.

i.e. There may be a more elegant way to detect when script sessions has been invalidated.

class RoomManager {

  Map<String, List<ScriptSession>> subscriptions = new HashMap<String, Set<ScriptSession>>();

  public syncronized void connect(String room) {
    Set<ScriptSession> set = subscriptions.get(room);
    if (set == null) {
        set =  new HashSet<ScriptSession>();
        subscriptions.put(room, set);
    }
    set.add( WebContextFactory.get().getScriptSession() );
  }

  public syncronized void disconnect(String room) {
    Set<ScriptSession> set = subscriptions.get(room);
    if (set != null) set.remove( WebContextFactory.get().getScriptSession() );
  }

  private syncronized void sendScriptToRoom(ScriptBuffer script, String room) {

    // should probably use an iterator here, and remove the scriptSession from the room if it is invalidated

     for (ScriptSession scrpitSession : rooms.get(room)) {
        if (!scrpitSession.isInvalidated()) {
             scrpitSession.addScript(script);
        }

    }
  }



// your method to generate the ScriptBuffer to send via sendScriptToRoom

  public void sendMessage(String room, String message) {

   ScriptBuffer script = new ScriptBuffer();
    script.appendScript("onMessage(");
    script.appendData(message");
    script.appendScript(")");
    sendScriptToRoom(room, script);
  }
}

Then, in your JSP, you can do something like this :
<head>
    <script>
        var roomID = "<%=StringUtils.escapeJavaScript(request.getParameter("roomID"))%>";
       onMessage = function(message) {
          alert(message)
      }
    </script>
</head>
<body onload='RoomManager.connect(roomID); RoomManager.sendMessage(roomID, "hello world");'  onunload='RoomManager.disconnect(roomID)'
>

</body>

On Mon, 2007-09-17 at 05:39 -0700, stojadinovicp wrote:
:confused:

Hi everyone!

In short, the problem is the following. Its an online card game with Rooms
and Tables organization. Now, one JSP is used to opened different rooms,
naturally. Same goes for tables. Depending on the params passed, like
"room/index.jsp?roomID=NewOrleans" for example, and then another room is
accessed by "room/index.jsp?roomID=BabyBlue"

The problem is that when I use:
	String currentPage = wctx.getCurrentPage();
	Collection<ScriptSession> sessions =
wctx.getScriptSessionsByPage(currentPage);
	for (ScriptSession ss : sessions) ss.addScript(new ScriptBuffer(js));

then ALL rooms get ALL messages :(((
So, if a user chats in one room, this goes to all the rooms :(((

It does make sense to see "room/index.jsp" as one page regardless of the
"?roomID=BlaBla" part, but therein lies my problem :(

Now, one obvious solution is to include the roomID in the JavaScript call
and then if the roomID is not valid I ignore the message. BUT, this sucks
big time because the idea is to have a few rooms but each of these should
have many tables opened at the same time. So there will be a LOT of messages
flying around and being ignored. In other words, one table page will get ALL
messages from ALL tables in ALL rooms.

I would REALLY like to avoid sending THIS much data to my users :(

Any ideas how to solve this? PLEASE!
ANY idea is welcome! And I do have a deadline :(((

THANKS!!!

Re: Same page different params!

by stojadinovicp :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

I managed to hack up one solution.

Since I already had some user management I simply extended it in the following way.
When user opens a page there is a call to userEntered method. In here I create an instance of UserSession which has two members, username and ScriptSession. ScriptSession you get from wctx.getScriptSession() (this is from the article above) This UserSession is then added to List<UserSession> sessions.

From then on I send messages with
for (UserSession s : sessions) s.addScript(js);
and thats it. (the addScript method has one line: ss.addScript(new ScriptBuffer(js));)

Now, I also have userLeft method which gets called on page onunload event or on a user ping timeout. (users send a ping every few seconds constantly)
in userLeft method I simply remove the UserSession from sessions List and thats it.

Tested on two rooms, works fine.

I forgot to mention the important part:
I have a RoomManager class which gets static calls from the webpage and this is the one I defined in dwr.xml file.
However, this class has List<RoomServer> rooms where I have different RoomServers that have been started. (RoomServer is a Thread which handles in/out messages for one particular room)
And the above UserSession stuff and methods and everything is forwarded to a particular RoomServer by
RoomManager based on roomID parameter given by the page itself.

stojadinovicp wrote:
...So, if a user chats in one room, this goes to all the rooms :(((...

Re: Same page different params!

by stojadinovicp :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

Hi Cameron,

THANKS for your reply. As you may have seen I managed to hack up something already
It seems to do the same thing as your solution. Great minds think alike huh?

Still, THANKS a lot. If my solution breaks I will have an alternative to look at

Pedja

Cameron Braid wrote:
Here's a rough class (typed in my mail program and therefore not compiled, let alone tested) that could do this for you...