亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

Spring Boot 中具有不同憑證的多個 AWS SQS 隊列

Spring Boot 中具有不同憑證的多個 AWS SQS 隊列

千巷貓影 2023-08-16 17:53:49
我有一個 Spring Boot 應用程序,想要從多個 AWS SQS 隊列接收消息。這些隊列都有自己的憑據(遺憾的是我對此無能為力)。這些憑證都不能訪問其他隊列之一,它們都僅限于一個隊列。只需一個隊列和憑據,這很簡單。我只需提供 Bean 形式的憑據并用\AWSCredentialsProvider注釋我的方法。 但我不知道如何使用多個憑據來做到這一點。@SqsListener@EnableSqs注釋@SqsListener無法提供憑據、預配置AmazonSqs對象或其他任何有幫助的內容。我尋找一種通過擴展CredentialsProvider或AmazonSqs客戶端來將隊列映射到憑據的方法,但無濟于事。我什至嘗試將憑證注入 AmazonHttpClient 的標頭中,但這也是不可能的。我嘗試創建手動監聽 SQS 隊列所需的一切。但我堅持為SimpleMessageListenerContainer.所需的QueueMessageHandler僅在使用應用程序上下文創建為 bean 時才有效。否則它不會查找用 注釋的方法@SqsListener。遺憾的是,我能找到的唯一教程或示例要么使用 JMS(我想避免使用 JMS),要么僅使用@SqsListener一個隊列的注釋。還有其他方法可以為多個隊列提供不同的憑據嗎?
查看完整描述

2 回答

?
翻閱古今

TA貢獻1780條經驗 獲得超5個贊

在花了一些時間尋找更好的解決方案后,我堅持以下幾點:


package test;


import com.amazonaws.auth.AWSCredentialsProvider;

import com.amazonaws.regions.AwsRegionProvider;

import com.amazonaws.services.sqs.AmazonSQSAsync;

import com.amazonaws.services.sqs.AmazonSQSAsyncClientBuilder;

import test.TestDto;

import test.CustomQueueMessageHandler;

import org.slf4j.Logger;

import org.slf4j.LoggerFactory;

import org.springframework.cloud.aws.messaging.config.SimpleMessageListenerContainerFactory;

import org.springframework.cloud.aws.messaging.config.annotation.NotificationMessage;

import org.springframework.cloud.aws.messaging.config.annotation.NotificationSubject;

import org.springframework.cloud.aws.messaging.listener.SimpleMessageListenerContainer;

import org.springframework.cloud.aws.messaging.listener.SqsMessageDeletionPolicy;

import org.springframework.cloud.aws.messaging.listener.annotation.SqsListener;

import org.springframework.stereotype.Component;


@Component

public class TestQueue {


  private static final String QUEUE_NAME = "TestQueue";

  private static final Logger log = LoggerFactory.getLogger(TestQueue.class);


  public TestQueue(AWSCredentialsProvider credentialsProvider, AwsRegionProvider regionProvider) {

    AmazonSQSAsync client = AmazonSQSAsyncClientBuilder.standard()

        .withCredentials(credentialsProvider)

        .withRegion(regionProvider.getRegion())

        .build();


    // custom QueueMessageHandler to initialize only this queue

    CustomQueueMessageHandler queueMessageHandler = new CustomQueueMessageHandler();

    queueMessageHandler.init(this);

    queueMessageHandler.afterPropertiesSet();


    SimpleMessageListenerContainerFactory factory = new SimpleMessageListenerContainerFactory();

    factory.setAmazonSqs(client);

    factory.setQueueMessageHandler(queueMessageHandler);


    SimpleMessageListenerContainer simpleMessageListenerContainer = factory.createSimpleMessageListenerContainer();

    simpleMessageListenerContainer.setMessageHandler(queueMessageHandler);

    try {

      simpleMessageListenerContainer.afterPropertiesSet();

    } catch (Exception e) {

      throw new RuntimeException(e);

    }

    simpleMessageListenerContainer.start();

  }


  @SqsListener(value = QUEUE_NAME, deletionPolicy = SqsMessageDeletionPolicy.ON_SUCCESS)

  public void receiveMessage(@NotificationMessage TestDto dto, @NotificationSubject String subject) {

    log.info("Received SQS Message: \nSubject: {} \n{}", subject, dto);

  }

}

和習俗QueueMessageHandler:


package test;


import java.util.Collections;

import org.springframework.cloud.aws.messaging.listener.QueueMessageHandler;

import org.springframework.messaging.converter.MappingJackson2MessageConverter;


public class CustomQueueMessageHandler extends QueueMessageHandler {


  public void init(Object handler) {

    detectHandlerMethods(handler);

  }

}

的唯一目的CustomQueueMessageHandler是傳遞一個應該掃描 SQS 注釋的對象。由于我不使用 Spring Context 啟動它,因此它不會在每個 bean 中搜索注釋@SqsListener。但所有的初始化都隱藏在受保護的方法后面。這就是為什么我需要覆蓋該類以訪問這些 init 方法。


我不認為這是一個非常優雅的解決方案,手動創建所有 AWS 客戶端內容并調用 bean init 方法。但這是我能找到的唯一仍然可以訪問 AWS SQS 庫的所有功能的解決方案,例如轉換傳入消息和通知、刪除策略、隊列輪詢(包括故障處理)等。


查看完整回答
反對 回復 2023-08-16
?
慕無忌1623718

TA貢獻1744條經驗 獲得超4個贊

@Bean您可以為您希望使用 custom 的帳戶聲明不同的s @Qualifier。假設您在兩個不同的帳戶中有兩個 SQS 隊列。然后聲明兩個類型為 的 bean AmazonSQS。


@Qualifier("first")

@Bean public AmazonSQS amazonSQSClient() {

    return AmazonSQSClient.builder()

            .withCredentials(credentialsProvider())

            .withRegion(Regions.US_EAST_1)

            .build();

}


@Qualifier("second")

@Bean public AmazonSQS amazonSQSClient() {

    return AmazonSQSClient.builder()

            .withCredentials(anotherCredentialsProvider())

            .withRegion(Regions.US_EAST_1)

            .build();

}

然后在你的服務中,你可以為@Autowired他們服務。


@Autowired @Qualifier("second") private AmazonSQS sqsSecond;


查看完整回答
反對 回復 2023-08-16
  • 2 回答
  • 0 關注
  • 237 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號