The data browser is built for Chrome, Firefox, Safari, and IE9 and above. Please upgrade your browser, or download Google Chrome to get the best experience.
Back to Questions

Locking

7 votes     1 answer     3.76k views     

7

I have created a 2 person asyncronous game. I want players to get paired up with random other players, however this is difficult to do without writing any server side code.

Ideally I would want to have a person save a game request to Parse, then another could pull a game request from Parse and claim it. However there is nothing really stopping 2 players from pulling the same game request and both trying to claim it. Is there anyway to pull a game request and somehow lock it so no one else can pull it. Or is there another way to get this sort of functionality?

Thanks! Alex

I would also be interested in finding this out. You can possibly use the incrementKey: method to create some type of lock but I'm not sure how safe that is.

- David Rodriguez over 1 year ago

1 Answer

5

David's solution is clever and works (incrementKey is atomic). If a GameRequest object is created with a "challengers" : 0 value, then each challenger could call incrementKey:@"challengers". If, after save, the value of challengers is 1, then they are the first committed challenger. I particularly like this solution since it works for N player games as well. Similarly, you can use addUnique: (also atomic) to add a User ID to a list of challengers.

You might also consider a solution which uses push notifications to propose matchups. You can use this to break ties in the host (whichever challenger reaches the host first is paired) and to get the user's attention if he has left the application.

Would I need to do an additional fetch after the save, or does the GameRequest get updated as it is saved? If I do need to do an additional fetch, it seems like I could end up in a scenario where two challengers increment a GameRequest. Both see that the challengers key is 2, and both give up on it.

With the addUnique strategy would players add their playerID to the list of challengers, and then fetch the Game Request once more. Whoever is the first in the list is the selected challenger?

Thanks for your help!

- Alex Limpaecher over 1 year ago

-[PFObject addObject:forKey], -[PFObject addUniqueObject:forKey:], -[PFObject addUniqueObjectsFromArray:forKey], -[PFObject removeObject:forKey], -[PFObject removeObjectsInArray:forKey], -[PFObject incrementKey], and -[PFObject incrementKey:byAmount:] all atomically modify-and-return a value. You cannot end up in a situation where both (or neither) challenger sees themselves as successfully paired.

- Thomas Bouldin over 1 year ago

I'm rather new to Parse and surely late to this discussion but I'm also looking for an atomic test-and-set operation for the same reasons mentioned above. Seems like [PFObject incrementKey] & Co provide a solution. What I don't understand is where they return a value. The ObjC Api has no return value. What do I miss? Any help much appreciated. - Tino

- Tino Rachui over 1 year ago

The increment works with both your offline copy and with the save operation. For example, if you download an object with "foo" = 5 and, immediately after, the another client sets "foo" = 6, incrementKey will set your local copy of foo to 6. When you save, foo will be 7 on both your local copy and in Parse's cloud.

- Thomas Bouldin over 1 year ago

Got it! Thanks a lot.

- Tino Rachui over 1 year ago