예제 #1
0
        /// <summary>
        /// member_no로 부터 샤드 아이디 얻기
        /// </summary>
        /// <param name="user_no"></param>
        /// <returns></returns>
        public GameContext(Session session)
        {
            // 수평샤딩
            //  범용적인 구성 방법
            //            shard key는 일반적으로 유저를 기준으로 하는 accountId(memberId) 를 사용
            //            대상 테이블의 PK는 shard key + @ 로 사용을 권장(ex: accountId + itemId)
            //            분산은 range, modulo 를 일반적으로 사용하지만
            //                 최근 가입한 유저가 더 많은 트래픽을 유발할 수 있는 게임의 특성상 modulo연산 사용을 권장
            //            론칭 후 운영 중인 상태에서는 데이터를 재배치 하기 힘드므로
            //                 성능테스트 일정 이전엔 2개의 shard만 구성하고 성능테스트 결과에 따라 shard 갯수 최종 픽스


            //return user_no % 2;

            shard_id_ = Shard.GetShardId(session.member_no);
        }
예제 #2
0
 public LogContext(Session session)
 {
     shard_id_ = Shard.GetShardId(session.member_no);
 }
예제 #3
0
 public LogContext(long member_no)
 {
     shard_id_ = Shard.GetShardId(member_no);
 }
예제 #4
0
        /// <summary>
        ///
        /// </summary>
        /// <param name="entity_no"></param>
        /// <param name="is_read_db"></param>
        /// <returns></returns>
        public async Task <T> GetEntity(long member_no, long entity_no, bool is_read_db, bool is_dirty_update, bool is_dirty)
        {
            T   entity = null;
            var ret    = await Cache.Instance.GetDatabase().StringGetAsync($"{entity_name}:{entity_no}:{Shard.GetShardId(member_no)}");

            if (ret.HasValue == true)
            {
                entity = JsonConvert.DeserializeObject <T>(ret);
            }
            else if (is_read_db)
            {
                entity = await query.Get(member_no, entity_no);
                await SetEntity(entity, member_no);
            }

            if (is_dirty_update && entity != null)
            {
                entity.SetUpdater(async() =>
                {
                    await UpdateEntity(member_no, entity);
                });
            }

            if (entity != null)
            {
                entity.SetDirty(is_dirty);
            }

            return(entity);
        }
예제 #5
0
        public async Task <bool> RemoveEntities(long member_no, long user_no)
        {
            var db  = Cache.Instance.GetDatabase();
            var ret = await Cache.Instance.GetDatabase().StringGetAsync($"{entities_name}:{user_no}");

            if (ret.HasValue == true)
            {
                var entity_dic = JsonConvert.DeserializeObject <Dictionary <int, long> >(ret);
                foreach (var entity in entity_dic)
                {
                    await Cache.Instance.GetDatabase().KeyDeleteAsync($"{entity_name}:{entity.Value}:{Shard.GetShardId(member_no)}");
                }
            }

            await Cache.Instance.GetDatabase().KeyDeleteAsync($"{entities_name}:{user_no}");

            return(true);
        }
예제 #6
0
        public async Task <bool> RemoveEntity(long member_no, T entity)
        {
            var ret = await Cache.Instance.GetDatabase().StringGetAsync($"{entities_name}:{entity.GetUserNo()}");

            if (ret.HasValue == true)
            {
                var entity_dic = JsonConvert.DeserializeObject <Dictionary <int, long> >(ret);
                if (entity_dic.Remove(entity.GetKey()) == false)
                {
                    return(false);
                }

                // 케릭터 목록 캐싱
                await Cache.Instance.GetDatabase().StringSetAsync($"{entities_name}:{entity.GetUserNo()}", JsonConvert.SerializeObject(entity_dic), session_expire);
            }

            await Cache.Instance.GetDatabase().KeyDeleteAsync($"{entity_name}:{entity.GetValue()}:{Shard.GetShardId(member_no)}");

            return(true);
        }
예제 #7
0
        async Task CacheEntity(long member_no, T entity, bool is_change_entity_list)
        {
            if (is_change_entity_list)
            {
                var ret = await Cache.Instance.GetDatabase().StringGetAsync($"{entities_name}:{entity.GetUserNo()}");

                if (ret.HasValue == true)
                {
                    var entity_dic = JsonConvert.DeserializeObject <Dictionary <int, long> >(ret);
                    entity_dic[entity.GetKey()] = entity.GetValue();

                    // 케릭터 목록 캐싱
                    await Cache.Instance.GetDatabase().StringSetAsync($"{entities_name}:{entity.GetUserNo()}", JsonConvert.SerializeObject(entity_dic), session_expire);
                }
            }

            // 케릭터 캐싱
            await Cache.Instance.GetDatabase().StringSetAsync($"{entity_name}:{entity.GetValue()}:{Shard.GetShardId(member_no)}", JsonConvert.SerializeObject(entity), session_expire);
        }
예제 #8
0
 public async Task <bool> SetEntity(T entity, long member_no)
 {
     try
     {
         return(await Cache.Instance.GetDatabase().StringSetAsync($"{entity_name}:{entity.GetValue()}:{Shard.GetShardId(member_no)}", JsonConvert.SerializeObject(entity), session_expire));
     }
     catch (Exception ex)
     {
         Log.Error(ex.Message);
         return(false);
     }
 }