Ir para o conteúdo

Como faço para integrar uma API REST do API Gateway ao Amazon SQS e resolver erros comuns?

10 minuto de leitura
0

Quero integrar uma API REST do Amazon API Gateway ao Amazon Simple Queue Service (Amazon SQS) e solucionar erros de integração.

Resolução

Para integrar uma API REST do API Gateway ao Amazon SQS, use o protocolo de consulta da AWS ou o protocolo AWS JSON.

Para integrar uma API REST do API Gateway com o Amazon SQS, use o protocolo de consulta da AWS

Conclua as etapas a seguir:

  1. Crie uma fila do SQS.

  2. Crie um perfil do AWS Identity and Access Management (AWS IAM) para um serviço da AWS.
    Observação: em Serviço ou caso de uso, selecione API Gateway.

  3. Para permitir que você publique mensagens da API no Amazon SQS, anexe a seguinte política do Amazon SQS com permissões SendMessage:

    {  "Version": "2012-10-17",
      "Statement": [
        {
          "Effect": "Allow",
          "Resource": [
            "arn:aws:sqs:example-region:example-account-id:example-sqs-queue-name"
          ],
          "Action": [
            "sqs:SendMessage"
          ]
        }
      ]
    }

    Observação: substitua example-region pela sua região da AWS, example-account-id pelo ID da sua conta da AWS e example-sqs-queue-name pelo nome da sua fila do SQS.

  4. Crie uma API REST no API Gateway.

  5. No console do API Gateway, crie uma integração do Amazon SQS para sua API REST.

  6. Crie um recurso de API REST ou um Método de API REST:
    Na página Recursos, clique em Criar método.
    Em Tipo de método, selecione POST.
    Em Tipo de integração, selecione AWS Service.
    Em Região da AWS, selecione sua região.
    Em AWS Service, clique em Simple Queue Service (SQS).
    (Opcional) Em Subdomínio da AWS, insira o subdomínio usado pelo serviço da AWS. Verifique a documentação do serviço para confirmar a disponibilidade de um subdomínio. Na configuração de exemplo do Amazon SQS, mantenha em branco.
    Em Método HTTP, selecione POST.
    Em Tipo de ação, selecione Usar substituição de caminho.
    Em Substituição de caminho (opcional), digite o ID da sua conta e o nome da fila do SQS no seguinte formato: exemplo-id-conta/exemplo-nome-fila-sqs. Por exemplo: 1234567890/MySQSStandardQueue.
    Em Perfil de execução, insira o ARN do perfil do IAM.
    Em Tempo limite de integração, selecione uma opção para sua configuração.
    Continue a inserir suas informações de integração da API REST.
    Clique em Criar método.
    Selecione o método POST Solicitação de integração.
    Clique em Editar.
    Em Passagem do corpo da solicitação, selecione a opção de acordo com suas necessidades.
    Expanda Parâmetros de cabeçalhos de solicitações de URL.
    Selecione Adicionar parâmetro de cabeçalho de solicitação.
    Em Nome, insira Content-Type.
    Em Mapeado de, insira 'application/x-www-form-urlencoded'.
    Expanda Modelos de mapeamento.
    Clique em Adicionar modelo de mapeamento.
    Em Content-Type, insira application/json.
    No modelo, insira Action=SendMessage&MessageBody=$input.body e clique em Salvar.

  7. Implante a API REST.

  8. Para testar a configuração, envie a seguinte solicitação ao API Gateway:

    curl --location --request POST 'https://example-api-id.execute-api.example-region.amazonaws.com/example-stage/example-resource' \     --header 'Content-Type: application/json' \  
       --data-raw '{  
        "message": "Hello World"  
      }'
    

    Observação: substitua example-api-id pelo ID da sua API, example-region pela sua região, example-stage pelo nome do seu estágio de teste e example-resource pelo nome do seu recurso.
    Exemplo de resposta de integração bem-sucedida:

    {    "SendMessageResponse": {  
        "ResponseMetadata": {  
          "RequestId": "f879fb11-e736-52c0-bd29-a0f2d09ad90d"  
        },  
          "SendMessageResult": {  
            "MD5OfMessageAttributes": null,  
            "MD5OfMessageBody": "3fc759ac1733366f98ec4270c788fcd1",  
            "MD5OfMessageSystemAttributes": null,  
            "MessageId": "4c360c3c-08f4-4392-bc14-8b0c88e314a2",  
            "SequenceNumber": null  
        }  
      }  
    }

Para integrar uma API REST do API Gateway ao Amazon SQS, use o protocolo AWS JSON

Conclua as etapas a seguir:

  1. Crie uma fila do SQS.

  2. Crie um perfil do IAM para um serviço da AWS.
    Observação: em Serviço ou caso de uso, selecione API Gateway.

  3. Para permitir que você publique mensagens da API no Amazon SQS, anexe a seguinte política do Amazon SQS com permissões SendMessage:

    {    "Version": "2012-10-17",  
      "Statement": [  
        {  
          "Effect": "Allow",  
          "Resource": [  
            "arn:aws:sqs:example-region:example-account-id:example-sqs-queue-name"  
          ],  
          "Action": [  
            "sqs:SendMessage"  
          ]  
        }  
      ]  
    }
    

    Observação: substitua example-region pela sua região da AWS, example-account-id pelo ID da sua conta da AWS e example-sqs-queue-name pelo nome da sua fila do SQS.

  4. Crie uma API REST no API Gateway.

  5. No console do API Gateway, crie uma integração do Amazon SQS para sua API REST.

  6. Crie um recurso de API REST ou um Método de API REST:
    Na página Recursos, clique em Criar método.
    Em Tipo de método, selecione POST.
    Em Tipo de integração, selecione AWS Service.
    Em Região da AWS, selecione sua região.
    Em AWS Service, clique em Simple Queue Service (SQS).
    Em Subdomínio da AWS, mantenha em branco. Esse é um parâmetro opcional no qual você insere o subdomínio que um serviço da AWS usa. Verifique a documentação do serviço para confirmar a disponibilidade de um subdomínio.
    Em Método HTTP, selecione POST.
    Em Tipo de ação, selecione Usar substituição de caminho.
    Em Substituição de caminho, insira o caractere /.
    Em Perfil de execução, insira o ARN do perfil do IAM.
    Em Tempo limite padrão, escolha uma opção para sua configuração.
    Expanda Cabeçalhos de solicitação HTTP.
    Selecione Adicionar cabeçalho.
    Em Nome, insira Content-Type.
    Selecione Adicionar cabeçalho.
    Em Nome, insira X-Amz-Target.
    Selecione Criar método.
    Selecione o método POST Solicitação de integração.
    Clique em Editar.
    Em Passagem do corpo da solicitação, deixe como a opção padrão Quando nenhum modelo corresponder ao cabeçalho content-type da solicitação.
    Expanda Parâmetros de cabeçalhos de solicitações de URL.
    Selecione Adicionar parâmetro de cabeçalho de solicitação.
    Em Nome, insira Content-Type.
    Em Mapeado de, insira method.request.header.Content-Type.
    Selecione Adicionar parâmetro de cabeçalho de solicitação.
    Em Nome, insira X-Amz-Target.
    Em Mapeado de, insira method.request.header.X-Amz-Target.
    Selecione Salvar.

  7. Implante a API REST.

  8. Para testar a configuração, envie a seguinte solicitação ao API Gateway:

    curl --location --request POST 'https://example-api-id.execute-api.example-region.amazonaws.com/example-stage/example-resource' \  --header 'Content-Type:application/x-amz-json-1.0' \
      --header 'X-Amz-Target:AmazonSQS.SendMessage' \
      --data-raw '{
        "QueueUrl": "https://sqs.<region>.<domain>/<awsAccountId>/<queueName>/",
        "MessageBody": "This is a test message"
    }'

    Observação: substitua example-api-id pelo ID da sua API, example-region pela sua região, example-stage pelo nome do seu estágio de teste e example-resource pelo nome do seu recurso. Para encontrar seu valor de QueueUrl, verifique os detalhes da sua fila do Amazon SQS.

Exemplo de resposta de integração bem-sucedida:

{"MD5OfMessageBody":"fafb00f5732ab283681e124bf8747ed1","MessageId":"b5aef1f3-af31-49f2-9973-6f802f7753e6"}

Observação: a resposta esperada do protocolo AWS JSON é diferente do protocolo de consulta da AWS, mesmo para a mesma chamada de API.

Resolva erros comuns do SQS

Para resolver erros comuns do Amazon SQS, siga estas etapas de solução de problemas de acordo com a mensagem de erro que você recebeu.

Erro "UnknownOperationException"

É possível receber uma mensagem de erro "UnknownOperationException" tanto do protocolo de consulta da AWS quanto do protocolo AWS JSON.

Se você usa o protocolo de consulta da AWS, esse erro ocorre quando você não configura o Content-Type como "application/x-www-form-urlencoded" no cabeçalho HTTP da solicitação de integração. Você também vê esse erro quando não adiciona a ação SendMessage ao modelo de mapeamento da solicitação de integração. Para resolver esse erro, certifique-se de formatar Content-Type corretamente e incluir a ação SendMessage no modelo de mapeamento.

Se você usa o protocolo AWS JSON, vê esse erro quando não envia ou não configura corretamente os cabeçalhos Content-Type e X-Amz-Target. Para resolver esse erro, configure o cabeçalho Content-Type como "application/x-amz-json-1.0" e configure o cabeçalho X-Amz-Target como AmazonSQS.{SQS-Action} e inclua os dois cabeçalhos na solicitação.

Erro “AccessDenied”

É possível receber uma mensagem de erro "AccessDenied" tanto do protocolo de consulta da AWS quanto do protocolo AWS JSON.

Esse erro ocorre quando o perfil de execução da integração da API não tem a permissão sqs:SendMessage configurada para enviar mensagens à fila do SQS.

Você também vê esse erro ao usar o protocolo de consulta da AWS e passar caracteres especiais não suportados na string de carga útil do corpo da solicitação. Você deve codificar caracteres especiais para evitar esse erro. Adicione a função $util.urlEncode() no modelo de mapeamento para converter o corpo da solicitação de uma string em um formato codificado. Veja a seguir um exemplo de modelo de mapeamento:

Action=SendMessage&MessageBody=$util.urlEncode($input.body)

Se você usa uma fila FIFO (First-In-First-Out, Primeiro a entrar, primeiro a sair) do Amazon SQS, certifique-se de incluir o atributo MessageGroupId or MessageDeduplicationId. Veja a seguir um exemplo de modelo de mapeamento FIFO:

Action=SendMessage&MessageBody=$util.urlEncode($input.body)&MessageGroupId=$your-msg-group-id&MessageDeduplicationId=$your-msg-dedup-id

Observação: substitua your-msg-group-id pelo seu ID de grupo de mensagens e your-msg-dedup-id pelo seu ID de desduplicação de mensagens.

O exemplo a seguir inclui as permissões necessárias para enviar mensagens à fila do SQS:

{  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Resource": [
        "arn:aws:sqs:example-region:example-account-id:example-sqs-queue-name"
      ],
      "Action": [
        "sqs:SendMessage"
      ]
    }
  ]
}

Observação: substitua example-region pela sua região, example-account-id pelo ID da sua conta e example-sqs-queue-name pelo nome da sua fila do SQS.

Erro "KMS.AccessDeniedException"

É possível receber uma mensagem de erro "KMS.AccessDeniedException" tanto do protocolo de consulta da AWS quanto do protocolo AWS JSON.

Esse erro ocorre quando o perfil de execução de integração da API não consegue realizar operações por meio do AWS Key Management Service (AWS KMS). Para resolver este erro, configure as permissões para executar operações nas chaves do AWS KMS que estão anexadas à fila criptografada no lado do servidor do Amazon SQS.

O exemplo a seguir inclui as permissões necessárias para realizar operações nas chaves do KMS que estão anexadas à fila do SQS:

{  "Sid": "Allow use of the key",
  "Effect": "Allow",
  "Principal": {
    "AWS": "arn:aws:iam::example-account-id:role/example-api-gw-integration-execution-role"
  },
  "Action": [
    "kms:Encrypt",
    "kms:GenerateDataKey*",
    "kms:Decrypt"
  ],
  "Resource": "*"
}

Observação: substitua example-account-id pelo ID da sua conta e example-api-gw-integration-execution-role pelo nome do seu perfil de execução.

Erro “MalformedQueryString”

É possível receber um erro “MalformedQueryString” tanto do protocolo de consulta da AWS quanto do protocolo AWS JSON.

Esse erro ocorre quando caracteres especiais estão na string de carga útil do corpo da solicitação. Adicione a função $util.urlEncode() no modelo de mapeamento para converter o corpo da solicitação de uma string em um formato codificado. Veja a seguir um exemplo de modelo de mapeamento:

Action=SendMessage&MessageBody=$util.urlEncode($input.body)

Erro "SignatureDoesNotMatch"

É possível receber um erro "SignatureDoesNotMatch" ao usar o protocolo de consulta da AWS.

Esse erro ocorre quando o método HTTP da solicitação de integração é definido como GET em vez de POST. Para resolver esse erro, defina o método HTTP como POST.

Erro “InvalidAddress”

É possível receber uma mensagem de erro “InvalidAddress” ao usar o protocolo AWS JSON.

Esse erro ocorre quando o URL da fila do SQS na carga útil do corpo está incorreto. Para resolver esse erro, verifique o URL da fila do SQS direcionado pela chamada de API.

Erro “SerializationException”

É possível receber uma mensagem de erro “SerializationException” ao usar o protocolo AWS JSON.

Esse erro ocorre quando a carga útil do corpo não é um JSON válido. Por exemplo, seu JSON pode ter uma vírgula ausente ou extra, ou uma chave ausente ou extra. Para resolver esse erro, revice seu JSON para deixá-lo em um formato válido.

Erro “MissingRequiredParameterException”

É possível receber um erro “MissingRequiredParameterException” ao usar o protocolo AWS JSON.

Esse erro ocorre quando você não inclui um ou mais dos parâmetros necessários na carga útil do corpo. Os parâmetros necessários dependem da sua chamada de API. Por exemplo, você vê esse erro de uma chamada de API SendMessage quando o parâmetro MessageBody está ausente. Consulte a Referência de API do SQS para obter os parâmetros e a sintaxe necessários.

Informações relacionadas

Integre o Amazon API Gateway com o Amazon SQS para lidar com REST assíncrono APIs

Como uso o API Gateway como proxy para outro serviço da AWS?