기계 번역으로 제공되는 번역입니다. 제공된 번역과 원본 영어의 내용이 상충하는 경우에는 영어 버전이 우선합니다.
작업자 스레드에서 구성된 클라이언트 사용
Scorekeep은 작업자 스레드를 사용하여 사용자가 게임에서 이길 때 Amazon SNS에 알림을 게시합니다. 알림을 게시하는 작업은 결합된 요청 작업의 나머지를 수행할 때보다 더 많은 시간이 걸리며 클라이언트 또는 사용자에게 영향을 주지 않습니다. 따라서 이 작업을 비동기식으로 수행하는 것은 응답 시간을 개선하는 좋은 방법입니다.
그러나 Java용 X-Ray SDK는 스레드가 생성될 때 어떤 세그먼트가 활성화되었는지 알지 못합니다. 따라서 구성된 AWS SDK for Java 클라이언트를 스레드 내에서 사용하려고 하면 SegmentNotFoundException
이 발생하여 스레드가 충돌합니다.
예 web-1.error.log
Exception in thread "Thread-2" com.amazonaws.xray.exceptions.SegmentNotFoundException: Failed to begin subsegment named 'AmazonSNS': segment cannot be found.
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
...
이 문제를 해결하기 위해 애플리케이션에서 GetTraceEntity
를 사용하여 기본 스레드에서 세그먼트에 대한 참조를 가져오고 Entity.run()
를 사용하여 세그먼트의 컨텍스트에 대한 액세스 권한으로 작업자 스레드 코드를 안전하게 실행합니다.
예 src/main/java/scorekeep/MoveFactory.java
— 작업자 스레드에 추적 컨텍스트 전달하기
import com.amazonaws.xray.AWSXRay;
import com.amazonaws.xray.AWSXRayRecorder;
import com.amazonaws.xray.entities.Entity;
import com.amazonaws.xray.entities.Segment;
import com.amazonaws.xray.entities.Subsegment;
...
Entity segment = recorder.getTraceEntity();
Thread comm = new Thread() {
public void run() {
segment.run(() -> {
Subsegment subsegment = AWSXRay.beginSubsegment("## Send notification");
Sns.sendNotification("Scorekeep game completed", "Winner: " + userId);
AWSXRay.endSubsegment();
}
}
이제 Amazon SNS를 직접 호출하기 전에 요청이 해결되기 때문에 애플리케이션은 스레드에 대한 별도의 하위 세그먼트를 생성합니다. 이렇게 하면 X-Ray SDK가 Amazon SNS의 응답을 기록하기 전에 세그먼트를 닫지 않습니다. Scorekeep이 요청을 해결할 때 열려 있는 세그먼트가 없으면 Amazon SNS의 응답이 손실될 수 있습니다.
멀티스레딩에 대한 자세한 내용은 멀티스레드 애플리케이션에서 스레드 간 세그먼트 컨텍스트 전달 단원을 참조하십시오.