분산된 작업 집합을 단일 작업으로 조정합니다. 작업 중 하나라도 실패하는 경우 실패를 투명하게 처리하거나 수행된 작업을 취소합니다. 그래야 전체 작업이 성공하며 그렇지 않으면 전체가 실패합니다. 이는 일시적 예외, 오래 지속된 오류 및 프로세스 오류로 인해 실패한 작업을 복구하고 다시 시도하도록 함으로써 분산된 시스템에 복원력을 제공할 수 있습니다.
컨텍스트 및 문제점
애플리케이션은 여러 단계를 포함하고 그 중 일부가 원격 서비스를 호출하거나 원격 리소스에 액세스할 수 있는 작업을 수행합니다. 개별 단계는 서로 독립적일 수 있지만, 작업을 구현하는 애플리케이션 논리에 의해 조정됩니다.
애플리케이션은 가능하면 작업이 완료되도록 하고 원격 서비스 또는 리소스에 액세스할 때 발생할 수 있는 모든 오류를 해결하도록 합니다. 오류는 여러 가지 이유로 발생할 수 있습니다. 예를 들어, 네트워크가 정지되거나 통신이 중단되거나 원격 서비스가 응답하지 않거나 불안정한 상태에 있거나 원격 리소스를 리소스 제약 등으로 인해 일시적으로 액세스할 수 없는 경우입니다. 대부분의 경우 오류는 일시적인 것이며 다시 시도 패턴으로 처리할 수 있습니다.
애플리케이션이 쉽게 복구할 수 없는 더욱 영구적인 오류를 탐지하는 경우 시스템을 일관된 상태로 복원하여 전체 작업의 무결성을 보장할 수 있어야 합니다.
해결 방법
Scheduler 에이전트 감독자 패턴은 다음과 같은 행위자를 정의합니다. 이러한 행위자는 전체 작업의 일부로 수행하는 단계를 오케스트레이션합니다.
Scheduler는 실행할 작업을 구성하는 단계를 준비하고 작업을 오케스트레이션합니다. 이들 단계는 파이프라인 또는 워크플로에 결합할 수 있습니다. Scheduler는 이 워크플로의 단계가 올바른 순서대로 수행되도록 합니다. 각 단계를 수행할 때, Scheduler는 "단계가 아직 시작되지 않음", "단계 실행 중" 또는 "단계 완료" 등 워크플로의 상태를 기록합니다. 상태 정보에는 완료 제한 시간이라고 하는 단계를 끝내는 데 허용된 시간의 상한이 포함되어야 합니다. 원격 서비스 또는 리소스에 대한 액세스가 필요한 단계의 경우 Scheduler는 적절한 에이전트를 호출하여 수행할 작업에 대한 세부 정보를 전달합니다. Scheduler는 일반적으로 비동기 요청/응답 메시징을 사용하는 에이전트와 통신합니다. 이는 다른 분산 메시징 기술을 대신 사용할 수 있더라도 큐를 사용하여 구현할 수 있습니다.
Scheduler는 프로세스 관리자 패턴의 프로세스 관리자와 비슷한 기능을 수행합니다. 실제 워크플로는 일반적으로 Scheduler가 제어하는 워크플로 엔진에 의해 정의되고 구현됩니다. 이러한 방법은 Scheduler에서 워크플로의 비즈니스 논리를 분리합니다.
에이전트는 원격 서비스에 대한 호출 또는 작업에서 단계별로 참조된 원격 리소스에 대한 액세스를 캡슐화하는 논리를 포함합니다. 각 에이전트는 일반적으로 단일 서비스 또는 리소스에 대한 호출을 래핑하여 (나중에 설명되는 제한 시간 제약 조건에 따라) 적절한 오류 처리 및 재시도 논리를 구현합니다. 재시도 논리를 구현할 때 원격 서비스에서 중복 제거 논리에 사용할 수 있도록 모든 재시도 시도에서 안정적인 식별자를 전달합니다. Scheduler에 의해 실행되는 워크플로의 단계가 서로 다른 단계의 여러 서비스와 리소스를 사용하는 경우, 각 단계는 다른 에이전트를 참조할 수 있습니다(이는 패턴 구현 세부 정보임).
감독자는 Scheduler에서 수행되고 있는 작업 단계의 상태를 모니터링합니다. 이는 주기적으로 실행되고(빈도는 시스템에 따라 다름), Scheduler에서 유지 관리되는 단계의 상태를 검사합니다. 시간을 초과했거나 실패한 것으로 감지되면 적절한 에이전트를 통해 단계를 복구하거나 적절한 수정 작업을 실행합니다(단계 상태 수정 작업을 포함할 수 있음). 복구 또는 수정 작업은 Scheduler 및 에이전트에 의해 구현됩니다. 감독자는 이러한 작업이 수행되도록 요청합니다.
Scheduler, 에이전트 및 감독자는 논리적 구성 요소이며 이들의 물리적 구현은 사용되는 기술에 따라 달라집니다. 예를 들어 여러 논리 에이전트는 단일 웹 서비스의 일부로 구현할 수 있습니다.
Scheduler는 작업 진행률과 상태 저장소라고 하는 지속형 데이터 저장소에 있는 각 단계의 상태에 대한 정보를 유지 관리합니다. 감독자는 단계가 실패했는지 여부를 판단하기 위해 이러한 정보를 사용할 수 있습니다. 그림은 Scheduler, 에이전트, 감독자 및 상태 저장소 간의 관계를 보여줍니다.
참고
이 다이어그램에서는 단순화된 패턴 버전을 보여줍니다. 실제 구현에서 각 작업의 하위 집합을 동시에 실행하는 Scheduler의 여러 인스턴스가 있을 수 있습니다. 마찬가지로, 시스템은 각 에이전트 또는 여러 감독자의 여러 인스턴스를 실행할 수 있습니다. 이 경우 감독자는 실패한 같은 단계 및 작업을 복구하기 위해 경쟁하지 않도록 다른 작업과 신중하게 조정해야 합니다. 리더 선택 패턴은 이러한 문제에 대해 한 가지 해결책을 제공합니다.
애플리케이션이 작업을 실행할 준비가 되면 Scheduler에 요청을 제출합니다. Scheduler는 작업과 해당 단계에 대한 초기 상태 정보(예를 들어, 단계가 아직 시작되지 않음)를 상태 저장소에 기록한 다음 워크플로에 정의된 작업을 수행합니다. Scheduler가 각 단계를 시작하면 상태 저장소의 해당 단계의 상태 정보(예를 들어, 단계 실행 중)를 업데이트합니다.
단계가 원격 서비스 또는 리소스를 참조하는 경우, Scheduler는 적절한 에이전트에 메시지를 보냅니다. 메시지에는 작업에 대한 완료 제한 시간 외에도 에이전트가 서비스에 전달하거나 리소스에 액세스해야 하는 정보가 있습니다. 에이전트가 작업을 성공적으로 완료하면 Scheduler에 응답을 반환합니다. 그런 다음 Scheduler는 상태 저장소의 상태 정보(예를 들어 단계 완료)를 업데이트하고 다음 단계를 수행할 수 있습니다. 이 프로세스는 전체 작업이 완료될 때까지 계속됩니다.
에이전트는 작업을 수행하는 데 필요한 모든 재시도 논리를 구현할 수 있습니다. 그러나 에이전트가 완료 제한 시간이 만료되기 전에 작업을 완료하지 못하면 Scheduler는 작업이 실패했음으로 가정합니다. 이 경우 에이전트는 작업을 중단하고 Scheduler에 어떠한 것도 반환하지 않고(오류 메시지도 포함) 어떠한 형태의 복구도 시도하지 않습니다. 이러한 제한을 두는 이유는 단계가 시간을 초과했거나 실패한 후 에이전트의 다른 인스턴스가 실패한 단계를 실행하는 데 예약될 수 있기 때문입니다(이 프로세스는 나중에 설명).
에이전트가 실패하면 Scheduler는 응답을 받지 않습니다. 패턴은 시간을 초과한 단계와 완전히 실패한 단계를 구분하지 않습니다.
단계가 시간을 초과하거나 실패한 경우 상태 저장소에는 단계가 실행 중이지만 완료 제한 시간을 초과할 것임을 나타내는 레코드가 포함됩니다. 감독자는 이와 같은 단계를 찾아 복구하려 합니다. 한 가지 가능한 전략은 감독자가 완료 제한 값을 업데이트하여 단계를 완료할 시간을 연장한 다음, Scheduler에 메시지를 보내어 단계가 시간을 초과했다는 것을 나타내는 것입니다. 그런 다음, Scheduler는 이 단계를 반복할 수 있습니다. 그러나 이러한 설계의 경우 작업이 idempotent가 되어야 합니다. 시스템에는 일관성을 유지하기 위한 인프라가 포함되어야 합니다. 자세한 내용은 반복 가능한 인프라, 복원력과 가용성을 위한 Azure 애플리케이션 설계, 리소스 일관성 결정 가이드를 참조하세요.
감독자는 단계가 지속적으로 실패하거나 시간을 초과하는 경우 동일한 단계를 다시 시도하는 것을 방지해야 합니다. 이렇게 하면 감독자는 상태 저장소에서 상태 정보와 함께 각 단계에 대한 재시도 횟수를 유지 관리할 수 있습니다. 이 개수가 미리 정의된 임계값을 초과하면 감독자는 이 기간 동안 오류가 해결하기 위해 Scheduler에게 단계를 다시 시도해야 함을 알리기 전에 장시간 동안 기다리는 전략을 채택할 수 있습니다. 또는 감독자가 Scheduler에 메시지를 보내 트랜잭션 패턴을 구현하여 전체 작업의 실행 취소를 요청할 수 있습니다. 이러한 방법은 성공적으로 완료된 각 단계에 대한 보상 작업을 구현하는 데 필요한 정보를 제공하는 Scheduler와 에이전트에 따라 달라집니다.
이는 Scheduler와 에이전트를 모니터링하고 실패한 경우 다시 시작하기 위한 것이 아닙니다. 시스템의 이러한 측면은 이들 구성 요소가 실행되는 인프라에서 처리되어야 합니다. 마찬가지로, 감독자는 Scheduler에 의해 수행 중인 작업을 실행하는 실제 비즈니스 업무에 대해 알아서는 안 됩니다(이러한 작업이 실패한 경우 보상 방법 포함). 이는 Scheduler에 의해 구현되는 워크플로 논리를 위한 것입니다. 관리자의 유일한 책임은 단계가 실패했는지 여부를 판단하여 이를 반복할지 또는 취소할 실패한 단계를 포함하는 전체 작업을 조정하는 것입니다.
실패한 후 Scheduler가 다시 시작되거나 Scheduler에 의해 수행 중인 워크플로가 예기치 않게 종료된 경우, Scheduler는 실패했을 때 처리하고 있던 진행 중인 작업 상태를 판단하고 해당 지점에서 이 작업을 재개할 준비를 할 수 있어야 합니다. 이 프로세스의 구현 정보는 시스템에 따라 다를 수 있습니다. 작업을 복구할 수 없는 경우 이미 수행된 작업을 취소해야 할 수도 있습니다. 또한 트랜잭션 보상을 구현해야 할 수 있습니다.
이러한 패턴의 주요 장점은 예기치 않은 일시적 또는 복구할 수 없는 오류 발생 시 시스템이 복원력을 갖는다는 것입니다. 시스템은 자체적으로 복구되도록 구성할 수 있습니다. 예를 들어, 에이전트 또는 Scheduler가 실패하는 경우 새로운 에이전트 도는 Scheduler를 시작하고 감독자가 작업을 재개하도록 조정할 수 있습니다. 감독자가 실패하는 경우 다른 인스턴스가 시작되어 오류가 발생한 위치에서부터 재개할 수 있습니다. 감독자를 주기적으로 실행하도록 예약하는 경우 미리 정의된 간격 후 새 인스턴스가 자동으로 시작할 수 있습니다. 상태 저장소는 복원력을 더 높이기 위해 복제할 수 있습니다.
문제 및 고려 사항
이 패턴을 구현할 방법을 결정할 때 다음 사항을 고려해야 합니다.
이 패턴은 구현하기 어려울 수 있으며 시스템의 각 오류 모드의 철저한 테스트가 필요합니다.
Scheduler에 의해 구현되는 복구/재시도 논리는 복잡하며 상태 저장소에 보관된 상태 정보에 좌우됩니다. 또 지속형 데이터 저장소에 보상 트랜잭션을 구현하는 데 필요한 정보를 기록하는 데 필요할 수도 있습니다. 보상 트랜잭션도 실패할 수 있습니다.
감독자 실행 빈도가 중요해집니다. 연장된 기간 동안 실패한 단계가 애플리케이션을 차단하지 않도록 충분히 자주 실행해야 하지만 과도하게 실행되지 않도록 해야 합니다.
에이전트에 의해 수행된 단계는 한 번 이상 실행할 수 있습니다. 이들 단계를 구현하는 논리는 idempotent이 되어야 합니다.
이 패턴을 사용해야 하는 경우
클라우드와 같이 분산된 환경에서 실행되는 프로세스가 통신 오류 및/또는 작업 오류에 대해 유연해야 하는 경우 이 패턴을 사용합니다.
이 패턴은 원격 서비스를 호출하지 않거나 원격 리소스에 액세스하지 않는 작업에 적합하지 않을 수 있습니다.
워크로드 디자인
설계자는 Scheduler 에이전트 감독자 패턴을 워크로드 디자인에 사용하여 Azure Well-Architected Framework 핵심 요소에서 다루는 목표와 원칙을 해결하는 방법을 평가해야 합니다. 예시:
핵심 요소 | 이 패턴이 핵심 목표를 지원하는 방법 |
---|---|
안정성 디자인 결정은 워크로드가 오작동에 대한 복원력을 갖도록 하고 오류가 발생한 후 완전히 작동하는 상태로 복구 되도록 하는 데 도움이 됩니다. | 이 패턴은 상태 메트릭을 사용하여 오류를 감지하고 오작동의 영향을 완화하기 위해 작업을 정상 에이전트로 다시 라우팅합니다. - RE:05 중복성 - RE:07 자가 치유 |
성능 효율성은 크기 조정, 데이터, 코드의 최적화를 통해 워크로드가 수요를 효율적으로 충족하는 데 도움이 됩니다. | 이 패턴은 성능 및 용량 메트릭을 사용하여 현재 사용률을 검색하고 용량이 있는 에이전트로 작업을 라우팅합니다. 우선 순위가 낮은 작업보다 우선 순위가 높은 작업의 실행에 우선 순위를 지정하는 데 사용할 수도 있습니다. - PE:05 크기 조정 및 분할 - PE:09 중요 흐름 |
디자인 결정과 마찬가지로 이 패턴으로 도입될 수 있는 다른 핵심 요소의 목표에 대한 절충을 고려합니다.
예시
전자 상거래 시스템을 구현하는 웹 애플리케이션은 Microsoft Azure에 배포되었습니다. 사용자는 이 애플리케이션을 실행하여 제품을 검색하고 주문할 수 있습니다. 사용자 인터페이스는 웹 역할로 실행되고 애플리케이션의 주문 처리 요소는 작업자 역할의 집합으로 구현됩니다. 주문 처리 논리의 일부분은 원격 서비스 액세스를 포함하고 시스템의 이러한 측면은 일시적이거나 보다 오래 지속되는 오류를 발생시킬 수 있습니다. 이러한 이유로 설계자는 시스템의 주문 처리 요소를 구현하기 위해 Scheduler 에이전트 감독자 패턴을 사용했습니다.
고객이 주문할 때 애플리케이션은 주문을 설명하는 메시지를 작성하고 이 메시지를 큐에 게시합니다. 작업자 역할에서 실행되는 별도의 제출 프로세스는 메시지를 검색하고, 주문 세부 정보를 주문 데이터베이스에 삽입하며, 상태 저장소에 주문 프로세스에 대한 레코드를 만듭니다. 주문 데이터베이스와 상태 저장소에 삽입하는 작업은 동일한 작업의 일부로서 수행됩니다. 제출 프로세스는 이 두 가지 삽입 작업이 함께 완료되도록 설계되었습니다.
주문에 대해 제출 프로세스가 만드는 상태 정보에는 다음이 포함됩니다.
OrderID. 주문 데이터베이스의 주문 ID입니다.
LockedBy. 주문을 처리하는 작업자 역할의 인스턴스 ID입니다. Scheduler를 실행하는 작업자 역할의 인스턴스가 현재 여러 개 있을 수 있지만 각각의 주문은 단일 인스턴스에 의해서만 처리되어야 합니다.
CompleteBy. 주문이 처리되어야 하는 시간입니다.
ProcessState. 주문을 처리하는 작업의 현재 상태입니다. 가능한 상태는 다음과 같습니다.
- 보류 중. 주문이 생성되었지만 처리가 아직 시작되지 않았습니다.
- 처리 중. 주문이 현재 처리 중입니다.
- 처리됨. 주문을 성공적으로 처리했습니다.
- 오류. 주문 처리가 실패했습니다.
FailureCount. 주문에 대해 시도했던 처리 횟수입니다.
이 상태 정보에서 OrderID
필드는 새 주문의 주문 ID에서 복사됩니다. LockedBy
및 CompleteBy
필드는 null
(으)로 설정되고, ProcessState
필드는 Pending
(으)로 설정되며, FailureCount
필드는 0으로 설정됩니다.
참고
이 예에서 주문 처리 논리는 비교적 간단하고 원격 서비스를 호출하는 단일 단계만 있습니다. 좀 더 복잡한 다단계 시나리오에서 제출 프로세스는 다수의 단계를 포함하므로 상태 저장소에 다수의 레코드가 만들어지며, 각 레코드는 개별 단계의 상태를 설명합니다.
Scheduler는 또한 작업자 역할의 일부로서 실행되고 주문을 처리하는 비즈니스 논리를 구현합니다. 새 주문에 대해 폴링하는 Scheduler 인스턴스는 LockedBy
필드가 null이고 ProcessState
필드가 보류 중인 레코드의 상태 저장소를 검사합니다. Scheduler가 새 주문을 찾으면 고유한 인스턴스 ID를 가진 LockedBy
필드를 즉시 채우고 CompleteBy
필드를 적절한 시간에 설정하며 ProcessState
필드를 처리에 설정합니다. 코드는 Scheduler의 동시 인스턴스 두 개가 동시에 같은 주문을 처리하지 못하도록 단독성이며 원자성을 가지도록 설계됩니다.
그런 다음 Scheduler는 비즈니스 워크플로를 실행하여 주문을 비동기적으로 처리하여 상태 저장소의 OrderID
필드의 값을 전달합니다. 주문을 처리하는 워크플로는 주문 데이터베이스에서 주문 세부 정보를 검색하고 작업을 수행합니다. 주문 처리 워크플로의 단계가 원격 서비스를 호출해야 하는 경우 에이전트를 사용합니다. 워크플로 단계는 요청/응답 채널 역할을 하는 한 쌍의 Azure Service Bus 메시지 큐를 사용하여 에이전트와 통신합니다. 그림은 솔루션의 상위 수준 보기를 보여 줍니다.
워크플로 단계에서 에이전트로 전송된 메시지는 주문을 설명하고 완료 제한 시간을 포함합니다. 에이전트가 완료 제한 시간이 만료되기 전에 원격 서비스로부터 응답을 받는 경우, 워크플로가 수신 중인 Service Bus 큐에서 회신 메시지를 게시합니다. 워크플로 단계가 유효한 회신 메시지를 받은 경우, 처리를 완료하고 Scheduler는 주문 상태의 ProcessState
필드를 처리됨으로 설정합니다. 이 때 주문 처리가 성공적으로 완료됩니다.
에이전트가 원격 서비스로부터 응답을 받기 전에 완료 제한 시간이 만료되면 에이전트는 간단히 처리를 중단하고 주문 처리를 종료합니다. 마찬가지로, 주문을 처리하는 워크플로가 완료 제한 시간을 초과하면 역시 주문 처리를 종료합니다. 두 경우 모두 상태 저장소의 주문 상태가 처리 중으로 설정되어 있지만 완료 제한 시간은 주문 처리 시간이 지났고 프로세스가 실패한 것으로 간주됨을 나타냅니다. 원격 서비스에 액세스하는 에이전트 또는 주문을 처리하는 워크플로(혹은 둘 다)가 예기치 않게 종료되는 경우, 상태 저장소의 정보는 다시 처리 중으로 설정되며 결국 만료된 완료 제한 값을 가지게 됩니다.
에이전트가 원격 서비스에 연결하려는 동안 복구할 수 없고 지속적인 오류를 감지한 경우, 오류 응답을 워크플로로 다시 보낼 수 있습니다. Scheduler는 주문 상태를 오류로 설정하고 이벤트를 발생시켜 운영자에게 알립니다. 그러면 운영자는 실패 원인을 직접 해결하고 실패한 처리 단계를 다시 제출할 수 있습니다.
감독자는 상태 저장소를 정기적으로 검사하여 만료된 완료 제한 값을 가진 주문을 찾습니다. 감독자가 레코드를 찾으면 FailureCount
필드의 값을 올립니다. 오류 개수 값이 지정된 임계 값 이하인 경우, 감독자는 LockedBy
필드를 null로 재설정하고, CompleteBy
필드를 새 만료 시간으로 업데이트하며, ProcessState
필드를 보류 중으로 설정합니다. Scheduler의 인스턴스는 이 주문을 선택하고 이전처럼 처리합니다. 오류 개수 값이 지정된 임계값을 초과하면 실패 원인은 지속적인 것으로 간주됩니다. 감독자는 주문 상태를 오류로 설정하고 이벤트를 발생시켜 운영자에게 알립니다.
이 예에서 감독자는 별도의 작업자 역할에서 구현됩니다. (이 패턴에서 스케줄러 구성 요소와 혼동하지 않기 위해) Azure Scheduler 서비스를 사용하여 실행할 감독자 작업을 조정하기 위해 다양한 전략을 사용할 수 있습니다. Azure Scheduler 서비스에 대한 자세한 내용은 스케줄러 페이지를 방문하세요.
이 예에는 표시되지 않았지만 Scheduler는 주문을 제출했던 애플리케이션이 진행률과 주문 상태에 대해 계속 알려주도록 해야 할 수 있습니다. 애플리케이션과 Scheduler는 둘 사이의 종속성을 제거하기 위해 서로 격리됩니다. 애플리케이션은 어떤 Scheduler 인스턴스가 주문을 처리하는지 알지 못하며, Scheduler는 어떤 특정 애플리케이션 인스턴스가 주문을 게시했는지 인식하지 못합니다.
주문 상태를 보고하도록 허용하기 위해 애플리케이션은 자체의 프라이빗 응답 큐를 사용할 수 있습니다. 이 응답 큐의 세부 정보는 상태 저장소에 이 정보를 포함하는 제출 프로세스로 보낸 요청의 일부로서 포함됩니다. 그런 다음 Scheduler는 주문 상태(요청 받음, 주문 완료됨, 주문 실패함 등)를 나타내는 이 큐에 메시지를 게시합니다. 애플리케이션의 원본 요청과 관련될 수 있도록 주문 ID를 이들 메시지에 포함시켜야 합니다.
다음 단계
이 패턴을 구현할 때 다음 지침도 관련이 있을 수 있습니다.
비동기 메시징 입문. Scheduler 에이전트 감독자 패턴의 구성 요소는 일반적으로 서로 분리되어 실행되고 비동기적으로 통신합니다. 메시지 큐에 따라 비동기 통신을 구현하는 데 사용할 수 있는 몇 가지 방법에 대해 설명합니다.
참조 6: A Saga on Sagas. CQRS 패턴이 프로세스 관리자 를 사용하는 방법을 보여주는 예입니다(CQRS Journey 지침의 일부).
관련 참고 자료
이 패턴을 구현할 때 다음 패턴도 관련이 있을 수 있습니다.
재시도 패턴. 에이전트는 이 패턴을 사용하여 이전에 실패했던 원격 서비스 또는 리소스에 액세스하는 작업을 투명하게 재시도할 수 있습니다. 실패의 원인이 일시적이며 수정할 수 있다고 예상되는 경우 사용합니다.
회로 차단기 패턴. 에이전트는 원격 서비스 또는 리소스에 연결했을 때 해결하는 데 시간이 다소 걸리는 오류를 처리하는 데 이 패턴을 사용할 수 있습니다.
보상 트랜잭션 패턴. Scheduler에 의해 수행되고 있는 워크플로를 성공적으로 완료할 수 없는 경우, 이전에 수행한 작업을 취소해야 할 수도 있습니다. 보상 트랜잭션 패턴은 최종 일관성 모델을 따라 작업에 대해 이를 어떻게 수행할 수 있는지를 설명합니다. 이러한 유형의 작업은 일반적으로 복잡한 비즈니스 프로세스와 워크플로를 수행하는 Scheduler에 의해 구현됩니다.
리더 선택 패턴. 실패한 동일 프로세스 복구를 시도하지 않도록 하기 위해 감독자의 여러 인스턴스 작업을 조정해야 할 수도 있습니다. 리더 선택 패턴은 이를 수행하는 방법을 설명합니다.
Clemens Vasters 블로그의 클라우드 아키텍처: Scheduler-에이전트-감독자 패턴