Exemplo n.º 1
0
def act_createGame(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if user.gameId: raise BadFieldException('alreadyInGame')
	map_ = dbi.getXbyY('Map', 'id', data['mapId'])
	descr = None
	if 'gameDescription' in data:
		descr = data['gameDescription']
	randseed = math.trunc(time.time())
	if 'randseed' in data:
		randseed = data['randseed']
	ai = data['ai'] if 'ai' in data else 0
	if ai > map_.playersNum:
		raise BadFieldException('tooManyPlayersForMap')
	newGame = Game(data['gameName'], descr, map_, randseed, data['ai'] if 'ai' in\
		data else None)
	dbi.addUnique(newGame, 'gameName')
	initRegions(map_, newGame)
	
	if ai < map_.playersNum:
		user.game = newGame
		user.priority = 1
		user.inGame = True
		dbi.flush(user)
		if not misc.TEST_MODE:
			data['randseed'] = randseed
		dbi.updateGameHistory(user.game, data)
		
	return {'result': 'ok', 'gameId': newGame.id}
Exemplo n.º 2
0
def act_createGame(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if user.gameId: raise BadFieldException('alreadyInGame')
    map_ = dbi.getXbyY('Map', 'id', data['mapId'])
    descr = None
    if 'gameDescription' in data:
        descr = data['gameDescription']
    randseed = math.trunc(time.time())
    if 'randseed' in data:
        randseed = data['randseed']
    ai = data['ai'] if 'ai' in data else 0
    if ai > map_.playersNum:
        raise BadFieldException('tooManyPlayersForMap')
    newGame = Game(data['gameName'], descr, map_, randseed, data['ai'] if 'ai' in\
     data else None)
    dbi.addUnique(newGame, 'gameName')
    initRegions(map_, newGame)

    if ai < map_.playersNum:
        user.game = newGame
        user.priority = 1
        user.inGame = True
        dbi.flush(user)
        if not misc.TEST_MODE:
            data['randseed'] = randseed
        dbi.updateGameHistory(user.game, data)

    return {'result': 'ok', 'gameId': newGame.id}
Exemplo n.º 3
0
def act_joinGame(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if user.game: raise BadFieldException('alreadyInGame')
	game = dbi.getXbyY('Game', 'id', data['gameId'])
	if game.state != GAME_WAITING:
		raise BadFieldException('badGameState')
	maxPlayersNum = game.map.playersNum
	if len(game.players) >= maxPlayersNum:
		raise BadFieldException('tooManyPlayers')
	maxPriority = max(game.players, key=lambda x: x.priority).priority
	user.game = game
	user.inGame = True
	user.priority = maxPriority + 1
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok'}
Exemplo n.º 4
0
def act_joinGame(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if user.game: raise BadFieldException('alreadyInGame')
    game = dbi.getXbyY('Game', 'id', data['gameId'])
    if game.state != GAME_WAITING:
        raise BadFieldException('badGameState')
    maxPlayersNum = game.map.playersNum
    if len(game.players) >= maxPlayersNum:
        raise BadFieldException('tooManyPlayers')
    maxPriority = max(game.players, key=lambda x: x.priority).priority
    user.game = game
    user.inGame = True
    user.priority = maxPriority + 1
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok'}
Exemplo n.º 5
0
def act_selectRace(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if user.currentTokenBadge:
        raise BadFieldException('badStage')
    game = user.game
    if not (game and user.inGame):
        raise BadFieldException('notInGame')
    checkStage(GAME_SELECT_RACE, user)
    if (user.game.state == misc.GAME_START):
        user.game.state = misc.GAME_PROCESSING
    chosenBadge = game.getTokenBadge(data['position'])
    position = chosenBadge.pos
    tokenBadges = dbi.query(TokenBadge).order_by(TokenBadge.pos).all()
    tokenBadges = tokenBadges[:6]
    price = position
    if user.coins < price:
        raise BadFieldException('badMoneyAmount')
    raceId, specialPowerId = chosenBadge.raceId, chosenBadge.specPowId
    addUnits = callRaceMethod(raceId, 'turnStartReinforcements')
    tokensNum = races.racesList[raceId].initialNum + races.specialPowerList[
        specialPowerId].tokensNum
    user.coins += chosenBadge.bonusMoney - price
    user.currentTokenBadge = chosenBadge
    user.tokensInHand = tokensNum + addUnits
    chosenBadge.inDecline = False
    chosenBadge.bonusMoney = 0
    chosenBadge.totalTokensNum = tokensNum + addUnits
    chosenBadge.specPowNum = races.specialPowerList[specialPowerId].bonusNum
    chosenBadge.pos = None
    dbi.flush(chosenBadge)
    updateRacesOnDesk(game, position)
    dbi.updateHistory(user, GAME_SELECT_RACE, chosenBadge.id)
    dbi.updateGameHistory(game, data)
    return {'result': 'ok', 'tokenBadgeId': chosenBadge.id}
Exemplo n.º 6
0
def getMapState(mapId, gameId = None):
	map_ = dbi.getXbyY('Map', 'id', mapId)
	result = getShortMapState(map_)
	result['regions'] = list()
	constRegionAttrs = ['border', 'coast', 'mountain', 
		'sea', 'mine', 'farmland', 'magic', 'forest', 'hill', 'swamp', 'cavern']
	curRegionAttrs = ['tokenBadgeId', 'ownerId', 'tokensNum', 
		'holeInTheGround', 'encampment', 'dragon', 'hero', 'fortified', 'inDecline']
	for region in map_.regions:
		curReg = dict()
		toArray = lambda x: json.loads('{ "a" : ' + x + '}')['a']
		curReg['raceCoords'] = toArray(region.raceCoords)
		curReg['powerCoords'] = toArray(region.powerCoords)
		curReg['coordinates'] = toArray(region.coordinates)
		curReg['constRegionState'] = list()
		
		for i in range(len(constRegionAttrs)):
			attr = getattr(region, constRegionAttrs[i])
			if not attr: continue
			if constRegionAttrs[i] in ('mountain', 'forest', 'hill', 'swamp', 'sea', 'farmland'):
				curReg['landscape'] = constRegionAttrs[i]
			elif constRegionAttrs[i] in ('mine', 'cavern', 'magic'):
				curReg['bonus'] = constRegionAttrs[i]
			curReg['constRegionState'].append(constRegionAttrs[i])
			 
				
		curReg['adjacentRegions'] = region.getNeighbors()
		if gameId:
			curRegState = region.getState(gameId)
			curReg['currentRegionState'] = dict()
			for i in range(len(curRegionAttrs)):
				curReg['currentRegionState'][curRegionAttrs[i]] = getattr(curRegState, curRegionAttrs[i])
		result['regions'].append(curReg)
	return result
Exemplo n.º 7
0
def act_defend(data):			## Should be renamed to retreat
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if not (user.game and user.inGame): 
		raise BadFieldException('notInGame')
	tokenBadge = user.currentTokenBadge
	if not tokenBadge: raise BadFieldException('badStage')
	checkStage(GAME_DEFEND, user)
	attackedRegion = user.game.getDefendingRegion(user)
	raceId, specialPowerId = tokenBadge.raceId, tokenBadge.specPowId
	notAdjacentRegions = []
	for terr in tokenBadge.regions:
		if terr.region.id not in attackedRegion.getNeighbors():##~~
			notAdjacentRegions.append(terr.region.id)
	for region in data['regions']:
		if not 'regionId' in region:
			raise BadFieldException('badRegionId')				
		if not 'tokensNum' in region:	
			raise BadFieldException('badTokensNum')
		if not isinstance(region['regionId'], int):
			raise BadFieldException('badRegionId')
		if not isinstance(region['tokensNum'], int):
			raise BadFieldException('badTokensNum')
		if user.tokensInHand < region['tokensNum']:
			raise BadFieldException('notEnoughTokens')
		destination = user.game.map.getRegion(region['regionId'])
		destState = destination.getState(user.game.id)
		if  notAdjacentRegions and destination.id not in notAdjacentRegions  or destState.owner.id != user.id:
			raise BadFieldException('badRegion')
		destState.tokensNum += region['tokensNum']
		user.tokensInHand -= region['tokensNum']
	if user.tokensInHand:  raise BadFieldException('thereAreTokensInTheHand')
	dbi.updateHistory(user, GAME_DEFEND, tokenBadge.id)
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok'}
Exemplo n.º 8
0
def act_defend(data):  ## Should be renamed to retreat
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if not (user.game and user.inGame):
        raise BadFieldException('notInGame')
    tokenBadge = user.currentTokenBadge
    if not tokenBadge: raise BadFieldException('badStage')
    checkStage(GAME_DEFEND, user)
    attackedRegion = user.game.getDefendingRegion(user)
    raceId, specialPowerId = tokenBadge.raceId, tokenBadge.specPowId
    notAdjacentRegions = []
    for terr in tokenBadge.regions:
        if terr.region.id not in attackedRegion.getNeighbors():  ##~~
            notAdjacentRegions.append(terr.region.id)
    for region in data['regions']:
        if not 'regionId' in region:
            raise BadFieldException('badRegionId')
        if not 'tokensNum' in region:
            raise BadFieldException('badTokensNum')
        if not isinstance(region['regionId'], int):
            raise BadFieldException('badRegionId')
        if not isinstance(region['tokensNum'], int):
            raise BadFieldException('badTokensNum')
        if user.tokensInHand < region['tokensNum']:
            raise BadFieldException('notEnoughTokens')
        destination = user.game.map.getRegion(region['regionId'])
        destState = destination.getState(user.game.id)
        if notAdjacentRegions and destination.id not in notAdjacentRegions or destState.owner.id != user.id:
            raise BadFieldException('badRegion')
        destState.tokensNum += region['tokensNum']
        user.tokensInHand -= region['tokensNum']
    if user.tokensInHand: raise BadFieldException('thereAreTokensInTheHand')
    dbi.updateHistory(user, GAME_DEFEND, tokenBadge.id)
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok'}
Exemplo n.º 9
0
def act_selectRace(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if user.currentTokenBadge:
		raise BadFieldException('badStage')
	game = user.game
	if not (game and user.inGame): 
		raise BadFieldException('notInGame')
	checkStage(GAME_SELECT_RACE, user)
	if (user.game.state == misc.GAME_START):
                user.game.state = misc.GAME_PROCESSING
	chosenBadge = game.getTokenBadge(data['position'])
	position = chosenBadge.pos
	tokenBadges = dbi.query(TokenBadge).order_by(TokenBadge.pos).all()
	tokenBadges = tokenBadges[:6]
	price = position
	if user.coins < price : 
		raise BadFieldException('badMoneyAmount')
	raceId, specialPowerId = chosenBadge.raceId, chosenBadge.specPowId
	addUnits = callRaceMethod(raceId, 'turnStartReinforcements')
	tokensNum = races.racesList[raceId].initialNum + races.specialPowerList[specialPowerId].tokensNum					
	user.coins += chosenBadge.bonusMoney - price
	user.currentTokenBadge = chosenBadge
	user.tokensInHand = tokensNum + addUnits
	chosenBadge.inDecline = False
	chosenBadge.bonusMoney = 0
	chosenBadge.totalTokensNum = tokensNum + addUnits
	chosenBadge.specPowNum = races.specialPowerList[specialPowerId].bonusNum
	chosenBadge.pos = None
	dbi.flush(chosenBadge)
	updateRacesOnDesk(game, position)
	dbi.updateHistory(user, GAME_SELECT_RACE, chosenBadge.id)
	dbi.updateGameHistory(game, data)
	return {'result': 'ok', 'tokenBadgeId': chosenBadge.id}
Exemplo n.º 10
0
def act_leaveGame(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    game = user.game
    if not (game and user.inGame): raise BadFieldException('notInGame')
    misc_game.leave(user)
    dbi.updateGameHistory(game, data)
    return {'result': 'ok'}
Exemplo n.º 11
0
def act_getGameState(data):
    return {
        'result':
        'ok',
        'gameState':
        misc_game.getGameState(dbi.getXbyY('Game', 'id', data['gameId']))
    }
Exemplo n.º 12
0
def act_aiJoin(data):
    game = dbi.getXbyY('Game', 'id', data['gameId'])
    if game.state != GAME_WAITING:
        raise BadFieldException('badGameState')
    maxPlayersNum = game.map.playersNum
    if len(game.players) >= maxPlayersNum:
        raise BadFieldException('tooManyPlayers')
    maxPriority = max(game.players, key=lambda x: x.priority).priority if len(
        game.players) else 0
    aiCnt = len(filter(lambda x: x.isAI == True, game.players))
    sid = getSid()
    ai = User('AI%d' % sid, None, True)
    ai.sid = sid
    ai.gameId = game.id
    ai.isReady = True
    ai.priority = maxPriority + 1
    ai.inGame = True
    dbi.add(ai)
    dbi.flush(ai)
    game.aiRequiredNum -= 1
    readyPlayersNum = dbi.query(User).filter(User.gameId == game.id).filter(
        User.isReady == True).count()
    if maxPlayersNum == readyPlayersNum:
        misc_game.startGame(game, ai, data)
    return {'result': 'ok', 'sid': ai.sid, 'id': ai.id}
Exemplo n.º 13
0
def act_sendMessage(data):
    userId = dbi.getXbyY('User', 'sid', data['sid']).id
    msgTime = misc.generateTimeForTest() if misc.TEST_MODE else math.trunc(
        time.time())
    text = data['text']
    dbi.add(Message(userId, text, msgTime))
    return {'result': 'ok'}
Exemplo n.º 14
0
def act_leaveGame(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	game = user.game
	if not (game and user.inGame): raise BadFieldException('notInGame')
	misc_game.leave(user)
	dbi.updateGameHistory(game, data)
	return {'result': 'ok'}
Exemplo n.º 15
0
def act_loadGame(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	game = user.game
	if game: dbi.clearGame(game)
	for act in data['actions']:
		if act['action'] in ('register', 'uploadMap', 'login', 'logout', 'saveGame', 
							'loadGame', 'resetServer', 'createDefaultMaps'):
			raise BadFieldException('illegalAction')
		if 'userId' in act:
			user = dbi.getXbyY('User', 'id', act['userId'])
			del act['userId']
			act['sid'] = user.sid
			
	for act in data['actions']:
		res = doAction(act, False)
	return {'result': 'ok'}
Exemplo n.º 16
0
def act_redeploy(data):
	for rec in data['regions']:
		if not ('regionId' in rec and 'tokensNum' in rec):
			raise BadFieldException('badRegionId' if not 'regionId' in rec else 'badTokensNum')
		if not isinstance(rec['regionId'], int) or rec['regionId'] <= 0:
			raise BadFieldException('badRegionId')
		if not isinstance(rec['tokensNum'], int) or rec['tokensNum'] < 0:
			raise BadFieldException('badTokensNum')
			
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if not (user.game and user.inGame): 
		raise BadFieldException('notInGame')
	tokenBadge = user.currentTokenBadge
	if not tokenBadge: raise BadFieldException('badStage')
	checkStage(GAME_REDEPLOY, user)
	raceId, specialPowerId = tokenBadge.raceId, tokenBadge.specPowId
	if user.game.getLastState() != GAME_UNSUCCESSFULL_CONQUER:
                tokenBadge.totalTokensNum += callRaceMethod(raceId, 'turnEndReinforcements', user)
	unitsNum = tokenBadge.totalTokensNum
	if not unitsNum: raise BadFieldException('noTokensForRedeployment')
	if not tokenBadge.regions:
		raise BadFieldException('userHasNoRegions')
	for region in tokenBadge.regions: region.tokensNum = 0
	usedRegions = []
	for rec in data['regions']:
		if rec['regionId'] in usedRegions:
			raise BadFieldException('badRegion')
		regState = user.game.map.getRegion(rec['regionId']).getState(user.game.id)
		tokensNum = rec['tokensNum']
		if  regState.tokenBadge != user.currentTokenBadge: raise BadFieldException('badRegion')
		if tokensNum > unitsNum: raise BadFieldException('notEnoughTokensForRedeployment')
		regState.tokensNum = tokensNum		
		unitsNum -= tokensNum
		usedRegions.append(rec['regionId'])

	specAbilities = [
	{'name': 'encampments', 'cmd': 'setEncampments'},
	{'name': 'fortified', 'cmd': 'setFortified'},
	{'name': 'heroes', 'cmd': 'setHero'}]

	for specAbility in specAbilities:
		if specAbility['name'] in data:
			callSpecialPowerMethod(specialPowerId, specAbility['cmd'], tokenBadge, 
				data[specAbility['name']], data)

			
	if unitsNum: 
		if not regState:
			raise BadFieldException('thereAreTokensInHand')
		regState.tokensNum += unitsNum
	emptyRegions = filter( lambda x: not x.tokensNum, tokenBadge.regions)
	for region in emptyRegions:
		clearFromRace(region)	
		region.owner = None
		region.tokenBadge = None
	user.tokensInHand = 0
	dbi.updateHistory(user, GAME_REDEPLOY, user.currentTokenBadge.id)
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok'}
Exemplo n.º 17
0
def getSid():
	if not misc_const.TEST_MODE:
		random.seed(math.trunc(time.time()))
	sid = None
	while 1:
		sid = misc_const.generateSidForTest() if misc_const.TEST_MODE else random.getrandbits(30)
		if not dbi.getXbyY('User', 'sid', sid, False): break
	return sid
Exemplo n.º 18
0
def act_loadGame(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    game = user.game
    if game: dbi.clearGame(game)
    for act in data['actions']:
        if act['action'] in ('register', 'uploadMap', 'login', 'logout',
                             'saveGame', 'loadGame', 'resetServer',
                             'createDefaultMaps'):
            raise BadFieldException('illegalAction')
        if 'userId' in act:
            user = dbi.getXbyY('User', 'id', act['userId'])
            del act['userId']
            act['sid'] = user.sid

    for act in data['actions']:
        res = doAction(act, False)
    return {'result': 'ok'}
Exemplo n.º 19
0
def getSid():
    if not misc.TEST_MODE:
        random.seed(math.trunc(time.time()))
    sid = None
    while 1:
        sid = misc.generateSidForTest() if misc.TEST_MODE else random.getrandbits(22)
        if not dbi.getXbyY("User", "sid", sid, False):
            break
    return sid
Exemplo n.º 20
0
def getSid():
    if not misc.TEST_MODE:
        random.seed(math.trunc(time.time()))
    sid = None
    while 1:
        sid = misc.generateSidForTest(
        ) if misc.TEST_MODE else random.getrandbits(22)
        if not dbi.getXbyY('User', 'sid', sid, False): break
    return sid
Exemplo n.º 21
0
def act_aiExecute(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	gameId = user.game.id
	res = None
	for act in data['actions']:
		res = doAction(act, False)
		if res['result'] != 'ok': break
	gameState = getGameState(user.game)
	dbi.rollback()
	return {'result': res, 'gameState' : gameState}
Exemplo n.º 22
0
def act_decline(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if not (user.game and user.inGame): 
		raise BadFieldException('notInGame')
	if not user.currentTokenBadge: raise BadFieldException('badStage')
	checkStage(GAME_DECLINE, user)
	makeDecline(user)
	dbi.updateHistory(user, GAME_DECLINE, user.declinedTokenBadge.id)
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok'}
Exemplo n.º 23
0
def act_decline(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if not (user.game and user.inGame):
        raise BadFieldException('notInGame')
    if not user.currentTokenBadge: raise BadFieldException('badStage')
    checkStage(GAME_DECLINE, user)
    makeDecline(user)
    dbi.updateHistory(user, GAME_DECLINE, user.declinedTokenBadge.id)
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok'}
Exemplo n.º 24
0
def getFriendsInfo(game):
    turn = game.turn
    histEntry = filter(lambda x: x.turn == turn and x.state == misc.GAME_CHOOSE_FRIEND, game.history)
    if histEntry:
        return {"diplomatId": histEntry[0].userId, "friendId": histEntry[0].friend}
    histEntry = filter(lambda x: x.turn == turn - 1 and x.state == misc.GAME_CHOOSE_FRIEND, game.history)
    if histEntry:
        attackedUser = dbi.getXbyY("User", "id", histEntry[0].friend)
        if histEntry[0].user.priority > attackedUser.priority:
            return {"diplomatId": histEntry[0].userId, "friendId": histEntry[0].friend}
Exemplo n.º 25
0
def act_dragonAttack(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if not (user.game and user.inGame): 
		raise BadFieldException('notInGame')
	if not user.currentTokenBadge: raise BadFieldException('badStage')
	checkStage(GAME_CONQUER, user, ATTACK_DRAGON)
	callSpecialPowerMethod(user.currentTokenBadge.specPowId, 'dragonAttack', 
		user.currentTokenBadge, user.game.map.getRegion(data['regionId']).getState(
		user.game.id))
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok'}	
Exemplo n.º 26
0
def act_selectFriend(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if not (user.game and user.inGame):
        raise BadFieldException('notInGame')
    if not user.currentTokenBadgeId:
        raise BadFieldException('badStage')
    checkStage(GAME_CHOOSE_FRIEND, user)
    callSpecialPowerMethod(user.currentTokenBadge.specPowId, 'selectFriend',
                           user, data)
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok'}
Exemplo n.º 27
0
def act_selectFriend(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if not (user.game and user.inGame): 
		raise BadFieldException('notInGame')
	if not user.currentTokenBadgeId : 
		raise BadFieldException('badStage')
	checkStage(GAME_CHOOSE_FRIEND, user)
	callSpecialPowerMethod(user.currentTokenBadge.specPowId, 'selectFriend',
		user, data)
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok'}
Exemplo n.º 28
0
def getMapState(mapId, gameId=None):
    map_ = dbi.getXbyY("Map", "id", mapId)
    result = getShortMapState(map_)
    result["regions"] = list()
    constRegionAttrs = [
        "border",
        "coast",
        "mountain",
        "sea",
        "mine",
        "farmland",
        "magic",
        "forest",
        "hill",
        "swamp",
        "cavern",
    ]
    curRegionAttrs = [
        "tokenBadgeId",
        "ownerId",
        "tokensNum",
        "holeInTheGround",
        "encampment",
        "dragon",
        "fortified",
        "inDecline",
    ]  # fortified
    for region in map_.regions:
        curReg = dict()
        curReg["raceCoords"] = StrToArr(region.raceCoords) if region.raceCoords != "None" else None
        curReg["powerCoords"] = StrToArr(region.powerCoords) if region.powerCoords != "None" else None
        curReg["coordinates"] = StrToArr(region.coordinates) if region.coordinates != "None" else None
        curReg["bonusCoords"] = StrToArr(region.bonusCoords) if region.bonusCoords != "None" else None
        curReg["constRegionState"] = list()

        for i in range(len(constRegionAttrs)):
            attr = getattr(region, constRegionAttrs[i])
            if not attr:
                continue
            # if constRegionAttrs[i] in ('mountain', 'forest', 'hill', 'swamp', 'sea', 'farmland'):
            # 	curReg['landscape'] = constRegionAttrs[i]
            # elif constRegionAttrs[i] in ('mine', 'cavern', 'magic'):
            # 	curReg['bonus'] = constRegionAttrs[i]
            curReg["constRegionState"].append(constRegionAttrs[i])

        curReg["adjacentRegions"] = region.getNeighbors()
        if gameId:
            curRegState = region.getState(gameId)
            curReg["currentRegionState"] = dict()
            for i in range(len(curRegionAttrs)):
                curReg["currentRegionState"][curRegionAttrs[i]] = getattr(curRegState, curRegionAttrs[i])
        result["regions"].append(curReg)
    return result
Exemplo n.º 29
0
def act_dragonAttack(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if not (user.game and user.inGame):
        raise BadFieldException('notInGame')
    if not user.currentTokenBadge: raise BadFieldException('badStage')
    checkStage(GAME_CONQUER, user, ATTACK_DRAGON)
    callSpecialPowerMethod(
        user.currentTokenBadge.specPowId, 'dragonAttack',
        user.currentTokenBadge,
        user.game.map.getRegion(data['regionId']).getState(user.game.id))
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok'}
Exemplo n.º 30
0
def act_throwDice(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if not (user.game and user.inGame): 
		raise BadFieldException('notInGame')
	if not user.currentTokenBadge or not user.tokensInHand: 
		raise BadFieldException('badStage')
	checkStage(GAME_THROW_DICE, user)
	specialPowerId = user.currentTokenBadge.specPowId
	dice = callSpecialPowerMethod(specialPowerId, 'throwDice', user.game, data['dice'] if 'dice' in data else 0)
	dbi.updateHistory(user, GAME_THROW_DICE, user.currentTokenBadge.id, dice)
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok', 'dice': dice}	
Exemplo n.º 31
0
def getFriendsInfo(game):
	turn = game.turn
	histEntry = filter(lambda x : x.turn == turn and x.state == misc_const.GAME_CHOOSE_FRIEND,
		game.history)
	if histEntry:
		return {'diplomatId': histEntry[0].userId, 'friendId': histEntry[0].friend}
	histEntry = filter(lambda x : x.turn == turn - 1 and x.state == misc_const.GAME_CHOOSE_FRIEND,
		game.history)
	if histEntry:
		attackedUser = dbi.getXbyY('User', 'id', histEntry[0].friend)
		if histEntry[0].user.priority > attackedUser.priority:
			return {'diplomatId': histEntry[0].userId, 'friendId': histEntry[0].friend} 
Exemplo n.º 32
0
def act_throwDice(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if not (user.game and user.inGame):
        raise BadFieldException('notInGame')
    if not user.currentTokenBadge or not user.tokensInHand:
        raise BadFieldException('badStage')
    checkStage(GAME_THROW_DICE, user)
    specialPowerId = user.currentTokenBadge.specPowId
    dice = callSpecialPowerMethod(specialPowerId, 'throwDice', user.game,
                                  data['dice'] if 'dice' in data else 0)
    dbi.updateHistory(user, GAME_THROW_DICE, user.currentTokenBadge.id, dice)
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok', 'dice': dice}
Exemplo n.º 33
0
	def selectFriend(self, user, data):
		if not('friendId' in data and isinstance(data['friendId'], int)):
			raise BadFieldException('badFriendId')
		friend = dbi.getXbyY('User', 'id', data['friendId'])
		if friend.id == user.id or friend.game.id != user.game.id:
			raise BadFieldException('badFriend')

		curTurnHistory = filter(lambda x: x.turn == user.game.turn and 
			x.userId == user.id and x.state == GAME_CONQUER, user.game.history)
		if curTurnHistory:
			if friend.currentTokenBadge and filter(lambda x: x.warHistory.victimBadgeId == 
				friend.currentTokenBadge.id, curTurnHistory):
				raise BadFieldException('badFriend')

		dbi.updateHistory(user, GAME_CHOOSE_FRIEND, user.currentTokenBadge.id, 
			None, friend.id)
Exemplo n.º 34
0
	def selectFriend(self, user, data):
		if not('friendId' in data and isinstance(data['friendId'], int)):
			raise BadFieldException('badFriendId')
		friend = dbi.getXbyY('User', 'id', data['friendId'])
		if friend.id == user.id or friend.game.id != user.game.id:
			raise BadFieldException('badFriend')

		curTurnHistory = filter(lambda x: x.turn == user.game.turn and 
			x.userId == user.id and x.state == GAME_CONQUER, user.game.history)
		if curTurnHistory:
			if friend.currentTokenBadge and filter(lambda x: x.warHistory.victimBadgeId == 
				friend.currentTokenBadge.id, curTurnHistory):
				raise BadFieldException('badFriend')

		dbi.updateHistory(user, GAME_CHOOSE_FRIEND, user.currentTokenBadge.id, 
			None, friend.id)
Exemplo n.º 35
0
def getNextPlayer(game):
    activePlayer = dbi.getXbyY("User", "id", game.activePlayerId)
    curPlayer = activePlayer
    while True:
        nextPlayer = filter(lambda x: x.priority > curPlayer.priority, game.players)
        if not len(nextPlayer):
            break
        nextPlayer = nextPlayer[0]
        if not nextPlayer.inGame:
            nextPlayer += countCoins(nextPlayer)["totalCoinsNum"]
            curPlayer = nextPlayer
        else:
            return nextPlayer
    game.turn += 1
    if game.turn == game.map.turnsNum:
        return game.end(activePlayer.coins)

    return filter(lambda x: x.priority >= 0 and x.inGame == True, game.players)[0]
Exemplo n.º 36
0
def act_setReadinessStatus(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    game = user.game
    if not (game and user.inGame):
        raise BadFieldException('notInGame')

    if game.state != GAME_WAITING:
        raise BadFieldException('badGameState')

    user.isReady = data['isReady']
    dbi.flush(user)
    maxPlayersNum = game.map.playersNum
    readyPlayersNum = dbi.query(User).filter(User.game == game).filter(
        User.isReady == True).count()
    if maxPlayersNum == readyPlayersNum:
        misc_game.startGame(game, user, data)
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok'}
Exemplo n.º 37
0
def act_setReadinessStatus(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	game = user.game
	if not (game and user.inGame): 
		raise BadFieldException('notInGame')

	
	if game.state != GAME_WAITING:
		raise BadFieldException('badGameState')

	user.isReady = data['isReady']
	dbi.flush(user)
	maxPlayersNum = game.map.playersNum
	readyPlayersNum = dbi.query(User).filter(User.game==game).filter(User.isReady==True).count()
	if maxPlayersNum == readyPlayersNum:
		misc_game.startGame(game, user, data)
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok'}
Exemplo n.º 38
0
def act_enchant(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if not (user.game and user.inGame):
        raise BadFieldException('notInGame')
    if not user.currentTokenBadge or user.currentTokenBadge.raceId != 9:
        raise BadFieldException('badStage')
    checkStage(GAME_CONQUER, user, ATTACK_ENCHANT)
    reg = user.game.map.getRegion(data['regionId']).getState(user.game.id)
    #print 'fff', reg.id, reg.tokenBadgeId
    if not reg.tokenBadge:
        raise BadFieldException('nothingToEnchant')
    victimBadgeId = reg.tokenBadge.id
    callRaceMethod(user.currentTokenBadge.raceId, 'enchant',
                   user.currentTokenBadge, reg)
    #clearFromRace(reg)
    dbi.updateWarHistory(user, victimBadgeId, user.currentTokenBadge.id, None,
                         reg.region.id, 1, ATTACK_ENCHANT)
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok'}
Exemplo n.º 39
0
def act_enchant(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if not (user.game and user.inGame): 
		raise BadFieldException('notInGame')
	if not user.currentTokenBadge or user.currentTokenBadge.raceId != 9: 
		raise BadFieldException('badStage')
	checkStage(GAME_CONQUER, user, ATTACK_ENCHANT)
	reg = user.game.map.getRegion(data['regionId']).getState(user.game.id)
	#print 'fff', reg.id, reg.tokenBadgeId
	if not reg.tokenBadge:
		raise BadFieldException('nothingToEnchant')
	victimBadgeId = reg.tokenBadge.id
	callRaceMethod(user.currentTokenBadge.raceId, 'enchant', user.currentTokenBadge,
		reg)
	#clearFromRace(reg)
	dbi.updateWarHistory(user, victimBadgeId, user.currentTokenBadge.id, None, 
			reg.region.id, 1, ATTACK_ENCHANT)
	dbi.updateGameHistory(user.game, data)
	return {'result': 'ok'}	
Exemplo n.º 40
0
def getMapState(mapId, gameId=None):
    map_ = dbi.getXbyY('Map', 'id', mapId)
    result = getShortMapState(map_)
    result['regions'] = list()
    constRegionAttrs = [
        'border', 'coast', 'mountain', 'sea', 'mine', 'farmland', 'magic',
        'forest', 'hill', 'swamp', 'cavern'
    ]
    curRegionAttrs = [
        'tokenBadgeId', 'ownerId', 'tokensNum', 'holeInTheGround',
        'encampment', 'dragon', 'fortified', 'inDecline'
    ]  #fortified
    for region in map_.regions:
        curReg = dict()
        curReg['raceCoords'] = StrToArr(
            region.raceCoords) if region.raceCoords != "None" else None
        curReg['powerCoords'] = StrToArr(
            region.powerCoords) if region.powerCoords != "None" else None
        curReg['coordinates'] = StrToArr(
            region.coordinates) if region.coordinates != "None" else None
        curReg['bonusCoords'] = StrToArr(
            region.bonusCoords) if region.bonusCoords != "None" else None
        curReg['constRegionState'] = list()

        for i in range(len(constRegionAttrs)):
            attr = getattr(region, constRegionAttrs[i])
            if not attr: continue
            #if constRegionAttrs[i] in ('mountain', 'forest', 'hill', 'swamp', 'sea', 'farmland'):
            #	curReg['landscape'] = constRegionAttrs[i]
            #elif constRegionAttrs[i] in ('mine', 'cavern', 'magic'):
            #	curReg['bonus'] = constRegionAttrs[i]
            curReg['constRegionState'].append(constRegionAttrs[i])

        curReg['adjacentRegions'] = region.getNeighbors()
        if gameId:
            curRegState = region.getState(gameId)
            curReg['currentRegionState'] = dict()
            for i in range(len(curRegionAttrs)):
                curReg['currentRegionState'][curRegionAttrs[i]] = getattr(
                    curRegState, curRegionAttrs[i])
        result['regions'].append(curReg)
    return result
Exemplo n.º 41
0
def getNextPlayer(game):
    activePlayer = dbi.getXbyY('User', 'id', game.activePlayerId)
    curPlayer = activePlayer
    while True:
        nextPlayer = filter(lambda x: x.priority > curPlayer.priority,
                            game.players)
        if not len(nextPlayer):
            break
        nextPlayer = nextPlayer[0]
        if not nextPlayer.inGame:
            nextPlayer += countCoins(nextPlayer)['totalCoinsNum']
            curPlayer = nextPlayer
        else:
            return nextPlayer
    game.turn += 1
    if (game.turn == game.map.turnsNum):
        return game.end(activePlayer.coins)

    return filter(lambda x: x.priority >= 0 and x.inGame == True,
                  game.players)[0]
Exemplo n.º 42
0
def getFriendsInfo(game):
    turn = game.turn
    histEntry = filter(
        lambda x: x.turn == turn and x.state == misc.GAME_CHOOSE_FRIEND,
        game.history)
    if histEntry:
        return {
            'diplomatId': histEntry[0].userId,
            'friendId': histEntry[0].friend
        }
    histEntry = filter(
        lambda x: x.turn == turn - 1 and x.state == misc.GAME_CHOOSE_FRIEND,
        game.history)
    if histEntry:
        attackedUser = dbi.getXbyY('User', 'id', histEntry[0].friend)
        if histEntry[0].user.priority > attackedUser.priority:
            return {
                'diplomatId': histEntry[0].userId,
                'friendId': histEntry[0].friend
            }
Exemplo n.º 43
0
def act_aiJoin(data):
	game = dbi.getXbyY('Game', 'id', data['gameId'])
	if game.state != GAME_WAITING:
		raise BadFieldException('badGameState')
	maxPlayersNum = game.map.playersNum
	if len(game.players) >= maxPlayersNum:
		raise BadFieldException('tooManyPlayers')
	maxPriority = max(game.players, key=lambda x: x.priority).priority if len(game.players) else 0
	aiCnt = len(filter(lambda x: x.isAI == True, game.players))
	sid = getSid()
	ai = User('AI%d' % sid, None, True)
	ai.sid = sid
	ai.gameId = game.id
	ai.isReady = True
	ai.priority = maxPriority + 1
	ai.inGame = True
	dbi.add(ai)
	dbi.flush(ai)
	game.aiRequiredNum -= 1
	readyPlayersNum = dbi.query(User).filter(User.gameId == game.id).filter(User.isReady==True).count()
	if maxPlayersNum == readyPlayersNum:
		misc_game.startGame(game, ai, data)
	return {'result': 'ok', 'sid' : ai.sid, 'id' : ai.id}
Exemplo n.º 44
0
def act_finishTurn(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	if not (user.game and user.inGame): 
		raise BadFieldException('notInGame')
	game = user.game
	checkStage(GAME_FINISH_TURN, user)
	tokenBadge = user.currentTokenBadge
	if tokenBadge and callRaceMethod(tokenBadge.raceId, 'needRedeployment') and\
		game.getLastState() != GAME_REDEPLOY and game.getLastState() != GAME_CHOOSE_FRIEND :  
		raise BadFieldException('badStage')

	incomeCoins = countCoins(user)
	user.coins += incomeCoins['totalCoinsNum']
	user.tokensInHand = 0
	nextPlayer = getNextPlayer(game)

	dbi.updateHistory(user, GAME_FINISH_TURN, None)
	dbi.updateGameHistory(game, data)
	if isinstance(nextPlayer, dict):
		result = nextPlayer
	else:
		prepareForNextTurn(game, nextPlayer)
		result = {'result': 'ok', 'statistics': incomeCoins['statistics']}
	return result
Exemplo n.º 45
0
def act_finishTurn(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    if not (user.game and user.inGame):
        raise BadFieldException('notInGame')
    game = user.game
    checkStage(GAME_FINISH_TURN, user)
    tokenBadge = user.currentTokenBadge
    if tokenBadge and callRaceMethod(tokenBadge.raceId, 'needRedeployment') and\
     game.getLastState() != GAME_REDEPLOY and game.getLastState() != GAME_CHOOSE_FRIEND :
        raise BadFieldException('badStage')

    incomeCoins = countCoins(user)
    user.coins += incomeCoins['totalCoinsNum']
    user.tokensInHand = 0
    nextPlayer = getNextPlayer(game)

    dbi.updateHistory(user, GAME_FINISH_TURN, None)
    dbi.updateGameHistory(game, data)
    if isinstance(nextPlayer, dict):
        result = nextPlayer
    else:
        prepareForNextTurn(game, nextPlayer)
        result = {'result': 'ok', 'statistics': incomeCoins['statistics']}
    return result
Exemplo n.º 46
0
def act_saveGame(data):
    result = list()
    game = dbi.getXbyY('Game', 'id', data['gameId'])
    for action in game.gameHistory:
        result.append(json.loads(action.action))
    return {'result': 'ok', 'actions': result}
Exemplo n.º 47
0
def act_sendMessage(data):
	userId = dbi.getXbyY('User', 'sid', data['sid']).id
	msgTime = misc.generateTimeForTest() if misc.TEST_MODE else math.trunc(time.time())
	text = data['text']
	dbi.add(Message(userId, text, msgTime))
	return {'result': 'ok'}
Exemplo n.º 48
0
def act_logout(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	leave(user)
	user.sid = None
	return {'result': 'ok'}
Exemplo n.º 49
0
def act_saveGame(data):
	result = list()
	game = dbi.getXbyY('Game', 'id', data['gameId'])
	for action in game.gameHistory:
		result.append(json.loads(action.action))
	return {'result': 'ok', 'actions': result}
Exemplo n.º 50
0
def act_getGameState(data):
	return {'result': 'ok', 'gameState': misc_game.getGameState(dbi.getXbyY('Game', 'id', 
		data['gameId']))}
Exemplo n.º 51
0
def act_logout(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    leave(user)
    user.sid = None
    return {'result': 'ok'}
Exemplo n.º 52
0
def act_conquer(data):
    user = dbi.getXbyY('User', 'sid', data['sid'])
    game = user.game
    if not (game and user.inGame):
        raise BadFieldException('notInGame')
    if not user.currentTokenBadge or not user.tokensInHand:
        raise BadFieldException('badStage')
    checkStage(GAME_CONQUER, user)
    region = game.map.getRegion(data['regionId'])
    regState = region.getState(game.id)
    victimTokenBadge = regState.tokenBadge
    owner = regState.owner
    if owner == user and not regState.inDecline:
        raise BadFieldException('badRegion')
    tokenBadge = user.currentTokenBadge
    raceId, specialPowerId = tokenBadge.raceId, tokenBadge.specPowId
    if not regState.inDecline:
        user.checkForFriends(owner)
    f1 = callRaceMethod(raceId, 'canConquer', region, tokenBadge)
    f2 = callSpecialPowerMethod(specialPowerId, 'canConquer', region,
                                tokenBadge)
    if not (f1 and f2):
        raise BadFieldException('badRegion')
    regState.checkIfImmune()
    attackedRace = None
    attackedSpecialPower = None
    if regState.tokenBadge:
        attackedRace = regState.tokenBadge.raceId
        attackedSpecialPower = regState.tokenBadge.specPowId
    enemyDefenseBonus = 0
    if attackedRace:
        enemyDefenseBonus = callRaceMethod(attackedRace, 'defenseBonus')
    defense = regState.tokensNum
    unitPrice = max(
        misc.BASIC_CONQUER_COST + defense + region.mountain +
        regState.encampment + regState.fortified + enemyDefenseBonus +
        callRaceMethod(raceId, 'attackBonus', region, tokenBadge) +
        callSpecialPowerMethod(specialPowerId, 'attackBonus', region,
                               tokenBadge), 1)
    unitsNum = user.tokensInHand
    if unitsNum + 3 < unitPrice:
        raise BadFieldException('badTokensNum')
    t = user.game.getLastState() == misc.GAME_THROW_DICE
    dice = t and user.game.history[-1].dice
    if not dice and unitsNum < unitPrice:
        dice = misc_game.throwDice(game)
    unitPrice -= (dice or 0)
    unitPrice = max(unitPrice, 1)
    if unitsNum < unitPrice:
        dbi.updateHistory(user, GAME_UNSUCCESSFULL_CONQUER,
                          user.currentTokenBadge.id)
        tokenBadge.totalTokensNum += callRaceMethod(tokenBadge.raceId,
                                                    'turnEndReinforcements',
                                                    user)
        return {'result': 'badTokensNum', 'dice': dice}
    clearFromRace(regState)  # Not sure if it's necessary
    victimBadgeId = regState.tokenBadgeId
    regState.owner = user
    regState.tokenBadge = user.currentTokenBadge
    regState.inDecline = False
    regState.tokensNum = unitPrice
    if victimTokenBadge:
        callRaceMethod(victimTokenBadge.raceId, 'sufferCasualties',
                       victimTokenBadge)
        owner.tokensInHand += defense - callRaceMethod(victimTokenBadge.raceId,
                                                       'getCasualties')
    callRaceMethod(raceId, 'conquered', regState, tokenBadge)
    dbi.updateWarHistory(user, victimBadgeId, tokenBadge.id, dice, region.id,
                         defense, ATTACK_CONQUER)
    user.tokensInHand -= unitPrice
    dbi.updateGameHistory(game, data)
    return {
        'result': 'ok',
        'dice': dice
    } if (dice and not t) else {
        'result': 'ok'
    }
Exemplo n.º 53
0
def act_conquer(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	game = user.game
	if not (game and user.inGame): 
		raise BadFieldException('notInGame')
	if not user.currentTokenBadge or  not user.tokensInHand:
		raise BadFieldException('badStage') 
	checkStage(GAME_CONQUER, user)
	region = game.map.getRegion(data['regionId'])
	regState = region.getState(game.id)
	victimTokenBadge = regState.tokenBadge
	owner = regState.owner
	if owner == user and not regState.inDecline: 
		raise BadFieldException('badRegion')
	tokenBadge = user.currentTokenBadge
	raceId, specialPowerId = tokenBadge.raceId, tokenBadge.specPowId
	if not regState.inDecline:
		user.checkForFriends(owner)
	f1 = callRaceMethod(raceId, 'canConquer', region, tokenBadge)
	f2 = callSpecialPowerMethod(specialPowerId, 'canConquer',  region,  tokenBadge)
	if not (f1 and f2):
		raise BadFieldException('badRegion')
	regState.checkIfImmune()
	attackedRace = None
	attackedSpecialPower = None
	if regState.tokenBadge:
		attackedRace = regState.tokenBadge.raceId
		attackedSpecialPower = regState.tokenBadge.specPowId
	enemyDefenseBonus = 0
	if attackedRace:
		enemyDefenseBonus = callRaceMethod(attackedRace, 'defenseBonus')
	defense = regState.tokensNum
	unitPrice = max(misc.BASIC_CONQUER_COST + defense + region.mountain + 
		regState.encampment + regState.fortified +  enemyDefenseBonus +
		callRaceMethod(raceId, 'attackBonus', region, tokenBadge) + 
		callSpecialPowerMethod(specialPowerId, 'attackBonus', region, tokenBadge)
			, 1)
	unitsNum = user.tokensInHand
	if unitsNum + 3 < unitPrice:
		raise BadFieldException('badTokensNum') 
	t = user.game.getLastState() == misc.GAME_THROW_DICE
	dice = t and user.game.history[-1].dice
	if not dice and unitsNum < unitPrice : 
		dice = misc_game.throwDice(game)
	unitPrice -= (dice or 0)
	unitPrice = max(unitPrice, 1)
	if unitsNum < unitPrice:
		dbi.updateHistory(user, GAME_UNSUCCESSFULL_CONQUER, user.currentTokenBadge.id)
		tokenBadge.totalTokensNum += callRaceMethod(tokenBadge.raceId, 'turnEndReinforcements', user)
		return {'result': 'badTokensNum', 'dice': dice}
	clearFromRace(regState)					# Not sure if it's necessary
	victimBadgeId = regState.tokenBadgeId
	regState.owner = user
	regState.tokenBadge = user.currentTokenBadge
	regState.inDecline = False
	regState.tokensNum = unitPrice
	if victimTokenBadge:
		callRaceMethod(victimTokenBadge.raceId, 'sufferCasualties', victimTokenBadge)
		owner.tokensInHand += defense - callRaceMethod(victimTokenBadge.raceId, 'getCasualties')
	callRaceMethod(raceId, 'conquered', regState, tokenBadge)
	dbi.updateWarHistory(user, victimBadgeId, tokenBadge.id, dice, 
		region.id, defense, ATTACK_CONQUER)
	user.tokensInHand -= unitPrice
	dbi.updateGameHistory(game, data)
	return {'result': 'ok', 'dice': dice} if (dice and not t) else {'result': 'ok'}
Exemplo n.º 54
0
def act_doSmth(data):
	user = dbi.getXbyY('User', 'sid', data['sid'])
	return {'result': 'ok'}
Exemplo n.º 55
0
def act_redeploy(data):
    for rec in data['regions']:
        if not ('regionId' in rec and 'tokensNum' in rec):
            raise BadFieldException(
                'badRegionId' if not 'regionId' in rec else 'badTokensNum')
        if not isinstance(rec['regionId'], int) or rec['regionId'] <= 0:
            raise BadFieldException('badRegionId')
        if not isinstance(rec['tokensNum'], int) or rec['tokensNum'] < 0:
            raise BadFieldException('badTokensNum')

    user = dbi.getXbyY('User', 'sid', data['sid'])
    if not (user.game and user.inGame):
        raise BadFieldException('notInGame')
    tokenBadge = user.currentTokenBadge
    if not tokenBadge: raise BadFieldException('badStage')
    checkStage(GAME_REDEPLOY, user)
    raceId, specialPowerId = tokenBadge.raceId, tokenBadge.specPowId
    if user.game.getLastState() != GAME_UNSUCCESSFULL_CONQUER:
        tokenBadge.totalTokensNum += callRaceMethod(raceId,
                                                    'turnEndReinforcements',
                                                    user)
    unitsNum = tokenBadge.totalTokensNum
    if not unitsNum: raise BadFieldException('noTokensForRedeployment')
    if not tokenBadge.regions:
        raise BadFieldException('userHasNoRegions')
    for region in tokenBadge.regions:
        region.tokensNum = 0
    usedRegions = []
    for rec in data['regions']:
        if rec['regionId'] in usedRegions:
            raise BadFieldException('badRegion')
        regState = user.game.map.getRegion(rec['regionId']).getState(
            user.game.id)
        tokensNum = rec['tokensNum']
        if regState.tokenBadge != user.currentTokenBadge:
            raise BadFieldException('badRegion')
        if tokensNum > unitsNum:
            raise BadFieldException('notEnoughTokensForRedeployment')
        regState.tokensNum = tokensNum
        unitsNum -= tokensNum
        usedRegions.append(rec['regionId'])

    specAbilities = [{
        'name': 'encampments',
        'cmd': 'setEncampments'
    }, {
        'name': 'fortified',
        'cmd': 'setFortified'
    }, {
        'name': 'heroes',
        'cmd': 'setHero'
    }]

    for specAbility in specAbilities:
        if specAbility['name'] in data:
            callSpecialPowerMethod(specialPowerId, specAbility['cmd'],
                                   tokenBadge, data[specAbility['name']], data)

    if unitsNum:
        if not regState:
            raise BadFieldException('thereAreTokensInHand')
        regState.tokensNum += unitsNum
    emptyRegions = filter(lambda x: not x.tokensNum, tokenBadge.regions)
    for region in emptyRegions:
        clearFromRace(region)
        region.owner = None
        region.tokenBadge = None
    user.tokensInHand = 0
    dbi.updateHistory(user, GAME_REDEPLOY, user.currentTokenBadge.id)
    dbi.updateGameHistory(user.game, data)
    return {'result': 'ok'}