728x90
반응형
Spring Boot 내에서 이벤트, 경고, 에러 같은 중요한 상황을 감지하고 이를 관리자, 개발자에게 알리는 기능. 신속한 대응과 문제 해결을 돕는 데 중요한 역할을 한다.
- 장애 감지, 대응
- 서비스 가용성 유지
- 성능 모니터링
- 비용 절감
- 사용자 경험 향상
- 예방적 조치
AWS SNS 연동
Amazon Simple Notification Service: AWS의 클라우드 기반 메시징 서비스. 이를 사용하면 애플리케이션, 서비스 또는 시스템 간에 다양한 종류의 메세지를 안전하게 전송하고 관리 할 수 있다.
- 푸시 알람
- 다중 프로토콜 지원 (HTTP, HTTPS, SMS,email, SQS, Lambda 등 지원)
- 이벤트 기반 아키텍쳐
- 확장성과 신뢰성
- 미리 알림 및 모니터링
연동하기
AWS root 사용자로 접속 - IAM dashboard 접속 - Permissions policies(SNS 검색해서 나오는 3개 선택), Access Key(third party service) 생성
Simple Notification Service - topic 생성
properties 파일에 설정값 추가.
sns.topic.arn=arn:
aws.accessKey= accesskey
aws.secretKey= secret key
aws.region=ap-northeast-2 #서울
cloud.aws.region.static=ap-northeast-2 #서울
cloud.aws.stack.auto=false #저장소에 저장하지 않음
AWSConfig class 생성.
import lombok.Getter;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Configuration;
@Configuration
@Getter
public class AWSConfig {
@Value("${sns.topic.arn}")
private String sosTopicARN;
@Value("${aws.accessKey}")
private String accessKey;
@Value("${aws.secretKey}")
private String secretKey;
@Value("${aws.region}")
private String awsRegion;
}
SnsService
import software.amazon.awssdk.regions.Region;
import com.example.boardserver.config.AWSConfig;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import software.amazon.awssdk.auth.credentials.AwsBasicCredentials;
import software.amazon.awssdk.auth.credentials.AwsCredentialsProvider;
import software.amazon.awssdk.services.sns.SnsClient;
@Service
@RequiredArgsConstructor
public class SnsService {
private final AWSConfig awsConfig;
//aws 인증 객체를 만든다.
public AwsCredentialsProvider getAwsCredentials(String accessKeyId, String secretAccessKey) {
AwsBasicCredentials awsBasicCredentials = AwsBasicCredentials.create(accessKeyId,
secretAccessKey);
return() -> awsBasicCredentials;
}
public SnsClient getSnsClient(){
return SnsClient.builder()
.credentialsProvider(
getAwsCredentials(awsConfig.getAccessKey(), awsConfig.getSecretKey())
).region(Region.of(awsConfig.getAwsRegion())) //실제 sns config 에 있는 region 값을 가져옴
.build();
}
}
SnsController
@RestController
@RequiredArgsConstructor
@Log4j2
public class SnsController {
private final SnsService snsService;
private final AWSConfig awsConfig;
@PostMapping("/create-topic")
public ResponseEntity<String> createTopic(@RequestParam final String topicName) {
final CreateTopicRequest createTopicRequest = CreateTopicRequest.builder()
.name(topicName)
.build();
SnsClient snsClient = snsService.getSnsClient();
final CreateTopicResponse createTopicResponse = snsClient.createTopic(createTopicRequest);
if (!createTopicResponse.sdkHttpResponse().isSuccessful()) {
throw getResponseStatusException(createTopicResponse);
}
log.info("topic name : {} ", createTopicResponse.topicArn());
log.info("topic list: {}", snsClient.listTopics());
//자원 반납
snsClient.close();
return new ResponseEntity<>("TOPIC CREATING SUCCESSFULLY", HttpStatus.CREATED);
}
//구독
@PostMapping("/subscribe")
public ResponseEntity<String> subscribe(@RequestParam final String endPoint,
@RequestParam final String topicArn) {
final SubscribeRequest subscribeRequest = SubscribeRequest.builder()
.protocol("https")
.topicArn(topicArn)
.endpoint(endPoint)
.build();
SnsClient snsClient = snsService.getSnsClient();
final SubscribeResponse subscribeResponse = snsClient.subscribe(subscribeRequest);
if(!subscribeResponse.sdkHttpResponse().isSuccessful()){
throw getResponseStatusException(subscribeResponse);
}
log.info("topicARN to subscribe = " + subscribeResponse.subscriptionArn());
log.info("subscription list = " + snsClient.listSubscriptions());
snsClient.close();
return new ResponseEntity<>("TOPIC SUBSCRIBE SUCCESS", HttpStatus.OK);
}
//발행
@PostMapping("publish")
public String publish(@RequestParam final String topicArn,
@RequestBody Map<String, Object> message) {
SnsClient snsClient = snsService.getSnsClient();
final PublishRequest publishRequest = PublishRequest.builder()
.topicArn(topicArn)
.subject("HTTP ENDPOINT TEST MESSAGE")
.message(message.toString())
.build();
PublishResponse publishResponse = snsClient.publish(publishRequest);
log.info("message status:" + publishResponse.sdkHttpResponse().statusCode());
snsClient.close();
return "sent MSG ID = " + publishResponse.messageId();
}
private ResponseStatusException getResponseStatusException(SnsResponse snsResponse) {
return new ResponseStatusException(
HttpStatus.INTERNAL_SERVER_ERROR, snsResponse.sdkHttpResponse().statusText().get()
);
}
}
board-server2 arn 을 사용해 구독하고 발행해보자.'
endPoint는 webhook 에서.
topicArn 은 notiy2 arn 사용
요청 성공시 웹훅에 SubscribeURL 이 온다. 이 URL 바탕으로 실제 메세지를 발행할 수 있다.
url 들어가면 arn 값이 나옴.
728x90
'JAVA > 프로젝트' 카테고리의 다른 글
배포 자동화 - 이론. CICD, Gradle, Jenkins (0) | 2024.11.25 |
---|---|
스프링부트 Slack 알림 연동 (0) | 2024.11.25 |
성능테스트 - 리팩토링 (0) | 2024.11.21 |
성능 테스트 - Locust 설치, 이론 (1) | 2024.11.20 |
성능 테스트 진행- 테스트 종류와 툴, 진행할 시나리오 (0) | 2024.11.18 |