You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 5 Next »

메시징(유입차량)에따른 톨게이트 구현은 , 트래픽 처리를 위한 좋은 샘플로 보인다.

구현하려고 하는 톨게이트 모델

  • 하이패스와 현금게이트 비율은 3:7이며 비율 조정이 유연해야함
  • 하이패스는 기달림이 없음
  • 현금 게이트는 1~10초 랜덤한 대기발생 ( 실제 현금결제는 1분~3분 이상의 시간이걸린다)
  • 현금 게이트를 이용하는 사용자는, 동일 Type게이트에서 공평한 대기 분배가 이루어져야함 

액터 구현

하이패스 게이트

        public HigPassGateActor()
        {
            id = Guid.NewGuid().ToString();
            logger.Info($"하이패스 액터 생성:{id}");

            ReceiveAsync<string>(async msg =>
            {
                //하이패스는 그냥 지나가면됨
                logger.Debug($"{msg}");
            });
        }


현금정산소 게이트

        public CashGateActor()
        {
            rnd = new Random();

            id = Guid.NewGuid().ToString();
            logger.Info($"현금정산게이트 액터 생성:{id}");

            ReceiveAsync<string>(async msg =>
            {
                //현금정산에 걸리는시간 1~10초                 
                int delay = rnd.Next(1000, 10000);
                await Task.Delay(delay);
                logger.Debug($"{msg}-{delay}");
            });
        }


액터 성능전략 적용

라우터구성

	actor.deployment {
		/highpass-gate-pool {
			router = round-robin-pool
			nr-of-instances = 3
		}

		/cashpass-gate-pool {
			router = smallest-mailbox-pool
			nr-of-instances = 7
		}
	}

분배처리를 위해 가장 일반적으로 라운드 로빈을 사용한다. 라운드 로빈은 처리 시간이 빠르고 일정할때

가장 심플하고 많이 사용되는 분배처리 방식이다. 하이패스 게이트에서는 무난하게 적용해도 된다.

하지만 현금정산소의 경우?  완료시간에 걸리는 시간은 운전자의 역량, 정산담당자의 빠른 처리능력 복합적으로 적용되며

완료시간이 오래걸릴 뿐더러 , 처리 시간이 불규칙적이다. 

그래서, Akka에서 제공하는  Smallest-mailbox의 라우터를 이용할수 있으며 적합한 방식이다. 

  • RoundRobin : 단순하게 순차적으로
  • Smallest-MailBox : 대기열이 적은곳으로


Akka에서는 유용한 몇가지 라우터를 제공하며 이용할수 있습니다.

라우터에 대한 심화학습 : https://getakka.net/articles/actors/routers.html

스레드풀 구성

# 기본 스레드 풀 사용
fast-dispatcher {
	type = Dispatcher
	throughput = 2
}

# 기본 스레드 풀 사용
slow-dispatcher {
	type = Dispatcher
	throughput = 7
}

스레드 풀까지 고려한 설정을 일반적으로 할 필요는 없지만, 더 깊이있는 최적화를 한다고하면

위와같이 액터의 메시지 처리에 사용되는 스레드를 분리할수 있고 최적화 할수 있다.

위 값에대한 최적값은 트래픽의 패턴에 따라 최적값을 찾아야하며, 중요한것은 성능에따라 분리해야한다란것이다.


일반적으로 액터 동시처리능력은 throughput에의해 결정되며 100이상의 값을 충분히 커버한다.

위와 같이 분리한 이유는, 성능이 느린 액터로 인해 동시 처리능력이 충분히 빠른 액터도 대기가 걸릴수 있기때문이다.

즉 동시처리 전체 성능 10이란것을 현금 게이트가 다 점유를 한다고하면, 하이패스에 처리되는 메시지 자체가

대기에 걸릴수 있으며 이것은 우리가 원하는 성능이 아니다.


최종 설정이 적용된 코드

            services.AddAkkaActor<HigPassGateActorProvider>((provider, actorFactory) =>
            {
                var actor = actorFactory.ActorOf(Props.Create<HigPassGateActor>()
                    .WithDispatcher("fast-dispatcher")
                    .WithRouter(FromConfig.Instance), "highpass-gate-pool");
                return () => actor;
            });

            services.AddAkkaActor<CashGateActorProvider>((provider, actorFactory) =>
            {
                var actor = actorFactory.ActorOf(Props.Create<CashGateActor>()
                    .WithDispatcher("slow-dispatcher")
                    .WithRouter(FromConfig.Instance), "cashpass-gate-pool");
                return () => actor;
            });

라우터 전략과 각 라우티에 사용된 액터에 스레드 사용전략을 복합적으로적용한 코드



변경 소스 : https://github.com/psmon/AkkaForNetCore/commit/b24003bf16289e171111057174a970c9e45ef2ed



  • No labels