package com.game.manager;

import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

import com.data.util.ErrorCode;
import com.game.Global;
import com.game.MainServer;
import com.game.data.JoinRoomData;
import com.game.data.Room;
import com.game.room.state.RoomReloadState;
import com.taurus.core.plugin.redis.Redis;
import com.taurus.core.plugin.redis.RedisLock;
import com.taurus.core.util.StringUtil;
import com.taurus.permanent.data.Session;

import redis.clients.jedis.Jedis;

/**
 * 房间管理类
 * 
 *
 */
public class RoomManager {

	public ConcurrentHashMap<String, Room> tableMap;

	public RoomManager() {
		this.tableMap = new ConcurrentHashMap<String, Room>();
	}

	/**
	 * 进入房间
	 * @param sender
	 * @param session_key
	 * @param gid
	 */
	public void joinRoom(Session sender, String session_key, int gid, String gps_pos) {
		Jedis jedis = Redis.use().getJedis();
		try {
			if (!jedis.exists(session_key)) {
				MainServer.instance.sendResponse(gid, ErrorCode._NO_SESSION, null, sender);
				return;
			}
			
			String room_key = jedis.hget(session_key, "room");
			if(StringUtil.isEmpty(room_key)) {
				MainServer.instance.sendResponse(gid, ErrorCode.NO_ROOM_NUM, null, sender);
				return;
			}
			Map<String, String> room_map = null;
			RedisLock lock = new RedisLock(room_key, jedis);
			try {
				lock.lock();
				room_map = jedis.hgetAll(room_key);
				String status = room_map.get("status");
				if(StringUtil.isEmpty(status)) {
					Global.gameCtr.delRoomSeat(session_key, room_key);
					MainServer.instance.sendResponse(gid, ErrorCode.NO_ROOM_NUM, null, sender);
					return;
				}
				if (status.equals("3") || status.equals("2")) {
					Global.gameCtr.delRoomSeat(session_key, room_key);
					MainServer.instance.sendResponse(gid, ErrorCode.GROUP_ROOM_DEL, null, sender);
					return;
				}
			
				if (Global.gameId != Integer.parseInt(room_map.get("game"))) {
					Global.logger.error("joinRoom gameId:"+Global.gameId+" != gameId:" + Integer.parseInt(room_map.get("game")));
					MainServer.instance.sendResponse(gid, ErrorCode.NO_SERVICE, null, sender);
					return;
				}
			
				String room_id = room_map.get("id");
				Room room = null;
				if (this.tableMap.containsKey(room_id)) {
					room = this.tableMap.get(room_id);
					if (room.isDestroy) {
						MainServer.instance.sendResponse(gid, ErrorCode._FAILED, null, sender);
						return;
					}
				} else {
					room = MainServer.instance.newRoom(room_id, room_map);
					room.loadRedisPlayer();
					this.tableMap.put(room_id, room);
					room.start();
					room.stateMachine.changeState(Global.getState(RoomReloadState.class));
				}
				if (room.isActive() == false)
				{
					room.start();
				}
			
				sender.setHashId(session_key);
				final JoinRoomData jrd = new JoinRoomData();
				jrd.room = room;
				jrd.session_key = session_key;
				jrd.sender = sender;
				jrd.gps_pos = gps_pos;
				room.enqueueRunnable(new Runnable() {
					@Override
					public void run() {
						try {
							int result = Global.gameCtr.joinRoom(jrd, gid);
							if(result!=0) {
								MainServer.instance.sendResponse(gid, result, null, sender);
							}
							Global.logger.info(session_key + " join [" + jrd.room.room_key + "]!");
						}
						catch (Exception e) {
							Global.logger.error(e);
							MainServer.instance.sendResponse(gid, 500, null, sender);}
						}
				});
			}finally {
				lock.unlock(false);
			}
		} catch (Exception e) {
			Global.logger.error(e);
			MainServer.instance.sendResponse(gid, 500, null, sender);
		} finally {
			jedis.close();
		}
	}
	
	/**
	 * 解散房间
	 * @param roomid		房间ID
	 */
	public void dismissRoom(String roomid,boolean sendEvt) {
		Room room = this.tableMap.get(roomid);
		Jedis jedis0 = Redis.use("group1_db0").getJedis();
		RedisLock lock = new RedisLock(room.room_key, jedis0);
		try {
			lock.lock();
			room.destroy(sendEvt);
			this.tableMap.remove(roomid);
		}finally {
			lock.unlock();
		}
	}


}
