setUserVariables messes up ?

Post here your questions about Actionscript and Java server side extensions development.

Moderators: Lapo, Bax

Willem
Posts: 51
Joined: 26 Jul 2007, 15:43
Location: Netherlands

setUserVariables messes up ?

Post by Willem »

This java-code in a room extension:

Code: Select all

// Set userVariable 'readyForNewRound' on all players
User[] players = currRoom.getAllPlayers();
int numPlayers = players.length;
HashMap<String,UserVariable> userVars = new HashMap<String,UserVariable>();
userVars.put("readyForNewRound", new UserVariable("1",UserVariable.TYPE_BOOLEAN));
this.numPlayersReady = 0;
for(int i =0;i < numPlayers; i++){
	helper.setUserVariables(players[i], userVars, true);
	this.numPlayersReady++;
}
Results in this xml-code sended to the client:

Code: Select all

[ RECEIVED ]: <msg t='sys'><body action='uVarsUpdate' r='24'><vars><var n='readyForNewRound' t='b'><![CDATA[1]]></var></vars><user id='35' /></body></msg>, (len: 140)
userVarsUpdate
false
[ RECEIVED ]: <msg t='sys'><body action='uVarsUpdate' r='24'><vars><var n='readyForNewRound' t='b'><![CDATA[1]]></var></vars><user id='34' /><user id='34' /></body></msg>, (len: 156)
TypeError: Error #1009: Cannot access a property or method of a null object reference.
	at it.gotoandplay.smartfoxserver.handlers::SysHandler/handleUserVarsUpdate()
	at Function/http://adobe.com/AS3/2006/builtin::apply()
	at it.gotoandplay.smartfoxserver.handlers::SysHandler/handleMessage()
	at it.gotoandplay.smartfoxserver::SmartFoxClient/::xmlReceived()
	at it.gotoandplay.smartfoxserver::SmartFoxClient/::handleMessage()
	at it.gotoandplay.smartfoxserver::SmartFoxClient/::handleSocketData()
As you can see, the second userVarsUpdate has a double user-tag in it.
How can I change the serverside extension so that this error won't occur anymore ?
Willem
Posts: 51
Joined: 26 Jul 2007, 15:43
Location: Netherlands

Post by Willem »

Is it because the user-node gets appended to the response-buffer with the user-variables in the extension-helper in the second for loop ( where it iterates over all the connected rooms ) ?
User avatar
Lapo
Site Admin
Posts: 23438
Joined: 21 Mar 2005, 09:50
Location: Italy

Post by Lapo »

Nope, I believe the client receives the update before it gets the roomList... possible?

Keep in mind that before a user can receive such update he/she must be connected in at least one room.
Lapo
--
gotoAndPlay()
...addicted to flash games
Willem
Posts: 51
Joined: 26 Jul 2007, 15:43
Location: Netherlands

Post by Willem »

Keep in mind that before a user can receive such update he/she must be connected in at least one room.
Well, in fact, the user was connected to more than one room, that seemed to be the reason for the error.
I changed the code to make sure that the user was only connected to one room, and than everything was ok again.
flarb
Posts: 131
Joined: 15 Oct 2007, 21:07
Location: Home of the Body Bag
Contact:

Post by flarb »

I'm having this same problem, the currUser in handleUserVarsUpdate is null. So it is impossible to use uservars if your'e connected to more than one room? That kinda sucks.
User avatar
Lapo
Site Admin
Posts: 23438
Joined: 21 Mar 2005, 09:50
Location: Italy

Post by Lapo »

flarb wrote:I'm having this same problem, the currUser in handleUserVarsUpdate is null. So it is impossible to use uservars if your'e connected to more than one room? That kinda sucks.
Could you explain a little bit better what you're doing and what problem do you get?

Thanks
Lapo
--
gotoAndPlay()
...addicted to flash games
flarb
Posts: 131
Joined: 15 Oct 2007, 21:07
Location: Home of the Body Bag
Contact:

Post by flarb »

Well right now my game is set up so that each user is connected to a main lobby and a private game room. If I create a game room and create a user variable--the next person who joins crashes out because "currUser" in "handleUserVarsUpdate" is null. (I assume it's sending all the user vars to the joining client).

When I step through this function, the actual user variable is there but the user object is null.
User avatar
Lapo
Site Admin
Posts: 23438
Joined: 21 Mar 2005, 09:50
Location: Italy

Post by Lapo »

Thanks, I've added the issue to our to-do list.
We'll fix it in the next update.

Meanwhile I will provide a simple work-around as soon as possible so that you don't get the error and the variables are handled properly.

Hope it helps.
Lapo
--
gotoAndPlay()
...addicted to flash games
flarb
Posts: 131
Joined: 15 Oct 2007, 21:07
Location: Home of the Body Bag
Contact:

Post by flarb »

Yeah that's cool--worst case is I was going to use a room variable. It's just more of a pain in the ass because I have to do a little weirdness in my java plug in code.
flarb
Posts: 131
Joined: 15 Oct 2007, 21:07
Location: Home of the Body Bag
Contact:

Post by flarb »

BTW--when might you have this workaround? I'll put off my tasks related to features that need uservars until you patch it or whatever you have in mind.
User avatar
Lapo
Site Admin
Posts: 23438
Joined: 21 Mar 2005, 09:50
Location: Italy

Post by Lapo »

We'll release it after Easter vacation.

Cheers
Lapo
--
gotoAndPlay()
...addicted to flash games
flarb
Posts: 131
Joined: 15 Oct 2007, 21:07
Location: Home of the Body Bag
Contact:

Post by flarb »

Cool! Thanks!

I'll send you some Easter candy or something--since it's on sale. :)
User avatar
Lapo
Site Admin
Posts: 23438
Joined: 21 Mar 2005, 09:50
Location: Italy

Post by Lapo »

Here we go:

1. open the SysHandler.as file found under the it.gotoandplay.smartfoxserver.handlers package

2. look for the handleUserVarsUpdate method and replace it with the following:

Code: Select all

public function handleUserVarsUpdate(o:Object):void
{
	var userId:int = int(o.body.user.@id)
	var changedVars:Array
	var varOwner:User
	
	if (o.body.vars.toString().length > 0)
	{
		for each (var room:Room in sfs.getAllRooms())
		{
			varOwner = room.getUser(userId)
			
			if (varOwner != null)
			{
				changedVars = []
				populateVariables(varOwner.getVariables(), o.body, changedVars)
			}
		}
		
		var params:Object = {}
		params.user = sfs.getActiveRoom().getUser(userId) != null ? sfs.getActiveRoom().getUser(userId) : varOwner
		params.changedVars = changedVars

		var evt:SFSEvent = new SFSEvent(SFSEvent.onUserVariablesUpdate, params)
		sfs.dispatchEvent(evt)
	}
}
Let me know if you have any problems

Cheers
Lapo
--
gotoAndPlay()
...addicted to flash games
User avatar
Carl Lydon
Posts: 298
Joined: 12 Nov 2007, 16:15
Location: NYC

Post by Carl Lydon »

This bug is a pain! I get it when a user that has a particularly slow connection joins a room.

The worst thing about it is, it doesn't just mess up the one person that enters the room, it freezes everyone in the room.

I checked to see that the user doesn't join a room until they receive the

onRoomListUpdate

I wonder, since this is a problem I've seen a lot on the forums, why don't you send the onRoomListUpdate into along with the connection or login events, since everything has to be done in a certain order, and not much interesting stuff on our end gets done in this function?
User avatar
Carl Lydon
Posts: 298
Joined: 12 Nov 2007, 16:15
Location: NYC

Post by Carl Lydon »

Also, since doing things out of order can bring everyone else to a screeching halt, could that be a nice way for a hacker to mess things up for other users?
Post Reply