SQS DELETE - Deletar Mensagem da Fila
O que é este Node?
O SQS DELETE é o node responsável por remover permanentemente mensagens processadas de filas do AWS SQS.
Por que este Node existe?
Deletar mensagens após processamento é crucial para evitar duplicatas. O SQS DELETE existe para:
- Confirmar processamento: Sinalizar que mensagem foi processada com sucesso
- Evitar duplicatas: Impedir que mensagem seja processada novamente
- Limpar fila: Manter fila apenas com mensagens pendentes
- Controle de custo: Evitar armazenamento desnecessário
- Gestão de recursos: Liberar espaço na fila
- Auditoria: Confirmar conclusão do processamento
Como funciona internamente?
Quando o SQS DELETE é executado, o sistema:
- Autentica na AWS: Usa accessKeyId, secretAccessKey e region
- Valida receiptHandle: Verifica se é válido (obtido no receive)
- Remove mensagem: Deleta permanentemente da fila
- Libera visibilidade: Mensagem não volta mais
- Retorna sucesso: Confirma deleção
- Se inválido: Lança erro (handle expirado ou inválido)
- Se erro: Lança exceção
Código interno (aws-executors.service.ts:129-137):
case 'deleteMessage':
await sqs.deleteMessage({
QueueUrl: data.queueUrl,
ReceiptHandle: data.receiptHandle,
}).promise();
return {
success: true,
message: 'Message deleted successfully',
};
Quando você DEVE usar este Node?
Use SQS DELETE sempre que processar mensagem com sucesso:
Casos de uso:
- Após processamento: Deletar job executado com sucesso
- Confirmação de entrega: Remover após enviar email/notificação
- Pipeline concluído: Remover após etapa finalizar
- Validação bem-sucedida: Deletar após validar dados
- Integração completa: Remover após sincronizar sistemas
- Limpeza de fila: Remover mensagens obsoletas
- Workflow finalizado: Deletar após completar todas etapas
Quando NÃO usar SQS DELETE:
- Processamento falhou: Deixe mensagem para retry (ou DLQ)
- Validação falhou: Não delete se dados inválidos
- Processamento parcial: Não delete se não completou
- Auditoria necessária: Mova para fila de auditoria antes
ReceiptHandle: O Identificador Único
O que é: Token único retornado no receiveMessage() que identifica a mensagem.
Características:
- Único para cada receive (mesmo MessageId gera handles diferentes)
- Expira após visibility timeout
- Necessário para deletar
- Não pode ser reutilizado
Importante:
// ❌ ERRADO - usar MessageId
deleteMessage({ MessageId: "abc123" })
// ✅ CORRETO - usar ReceiptHandle
deleteMessage({ ReceiptHandle: "AQEBzW...xyz==" })
Parâmetros Detalhados
receiptHandle (string, obrigatório)
O que é: Token único obtido ao receber a mensagem, usado para identificá-la na deleção.
Onde obter: Campo ReceiptHandle da resposta de receiveMessages
Flow completo para testar:
{
"name": "Teste SQS Delete - Receipt Handle",
"nodes": [
{
"id": "start_1",
"type": "start",
"position": { "x": 100, "y": 100 },
"data": { "label": "Início" }
},
{
"id": "sqs_receive_1",
"type": "aws_sqs",
"position": { "x": 300, "y": 100 },
"data": {
"label": "Receber Mensagem",
"parameters": {
"operation": "receiveMessages",
"accessKeyId": "{{aws_access_key}}",
"secretAccessKey": "{{aws_secret_key}}",
"region": "us-east-1",
"queueUrl": "{{sqs_queue_url}}",
"maxMessages": 1
}
}
},
{
"id": "variable_1",
"type": "variable",
"position": { "x": 500, "y": 100 },
"data": {
"label": "Extrair Handle",
"parameters": {
"variable": "receiptHandle",
"value": "{{messages[0].ReceiptHandle}}"
}
}
},
{
"id": "message_1",
"type": "message",
"position": { "x": 700, "y": 100 },
"data": {
"label": "Processar",
"parameters": {
"message": "⚙️ Processando mensagem...\nID: {{messages[0].MessageId}}"
}
}
},
{
"id": "delay_1",
"type": "delay",
"position": { "x": 900, "y": 100 },
"data": {
"label": "Simular Processamento",
"parameters": {
"seconds": 5
}
}
},
{
"id": "sqs_delete_1",
"type": "aws_sqs",
"position": { "x": 1100, "y": 100 },
"data": {
"label": "Deletar Mensagem",
"parameters": {
"operation": "deleteMessage",
"accessKeyId": "{{aws_access_key}}",
"secretAccessKey": "{{aws_secret_key}}",
"region": "us-east-1",
"queueUrl": "{{sqs_queue_url}}",
"receiptHandle": "{{receiptHandle}}"
}
}
},
{
"id": "message_2",
"type": "message",
"position": { "x": 1300, "y": 100 },
"data": {
"label": "Confirmar",
"parameters": {
"message": "✅ Mensagem processada e deletada com sucesso!"
}
}
},
{
"id": "end_1",
"type": "end",
"position": { "x": 1500, "y": 100 },
"data": { "label": "Fim" }
}
],
"edges": [
{ "source": "start_1", "target": "sqs_receive_1" },
{ "source": "sqs_receive_1", "target": "variable_1" },
{ "source": "variable_1", "target": "message_1" },
{ "source": "message_1", "target": "delay_1" },
{ "source": "delay_1", "target": "sqs_delete_1" },
{ "source": "sqs_delete_1", "target": "message_2" },
{ "source": "message_2", "target": "end_1" }
]
}
Teste: Mensagem é recebida, processada e deletada. Não volta para fila.
queueUrl (string, obrigatório)
O que é: URL completa da fila SQS de onde a mensagem será deletada.
Deve ser a mesma URL usada no receiveMessages
Parâmetros
| Campo | Tipo | Obrigatório | Descrição |
|---|---|---|---|
| operation | string | Sim | Deve ser "deleteMessage" |
| accessKeyId | string | Sim | AWS Access Key ID |
| secretAccessKey | string | Sim | AWS Secret Access Key |
| region | string | Sim | Região AWS |
| queueUrl | string | Sim | URL da fila SQS |
| receiptHandle | string | Sim | Token da mensagem (do receive) |
Exemplo 1: Processar e Deletar Pedido
Objetivo: Receber pedido, processar e confirmar deleção
JSON para Importar
{
"name": "Processar e Deletar Pedido",
"nodes": [
{
"id": "start_1",
"type": "start",
"position": { "x": 100, "y": 100 },
"data": { "label": "Início" }
},
{
"id": "message_1",
"type": "message",
"position": { "x": 300, "y": 100 },
"data": {
"label": "Iniciar Worker",
"parameters": {
"message": "🔄 Worker de pedidos iniciado..."
}
}
},
{
"id": "sqs_receive_1",
"type": "aws_sqs",
"position": { "x": 500, "y": 100 },
"data": {
"label": "Buscar Pedido",
"parameters": {
"operation": "receiveMessages",
"accessKeyId": "{{aws_access_key}}",
"secretAccessKey": "{{aws_secret_key}}",
"region": "sa-east-1",
"queueUrl": "https://sqs.sa-east-1.amazonaws.com/123456789012/orders-queue",
"maxMessages": 1,
"waitTimeSeconds": 20,
"visibilityTimeout": 300
}
}
},
{
"id": "condition_1",
"type": "condition",
"position": { "x": 700, "y": 100 },
"data": {
"label": "Tem Pedido?",
"parameters": {
"variable": "messages.length",
"operator": ">",
"value": "0"
}
}
},
{
"id": "variable_1",
"type": "variable",
"position": { "x": 900, "y": 50 },
"data": {
"label": "Extrair Dados",
"parameters": {
"variable": "order",
"value": "{{messages[0].Body}}"
}
}
},
{
"id": "message_2",
"type": "message",
"position": { "x": 1100, "y": 50 },
"data": {
"label": "Processar Pedido",
"parameters": {
"message": "📦 Processando pedido {{order.orderId}}\n💰 Valor: R$ {{order.total}}\n👤 Cliente: {{order.customer.name}}"
}
}
},
{
"id": "delay_1",
"type": "delay",
"position": { "x": 1300, "y": 50 },
"data": {
"label": "Simular Processamento",
"parameters": {
"seconds": 3
}
}
},
{
"id": "sqs_delete_1",
"type": "aws_sqs",
"position": { "x": 1500, "y": 50 },
"data": {
"label": "Confirmar Processamento",
"parameters": {
"operation": "deleteMessage",
"accessKeyId": "{{aws_access_key}}",
"secretAccessKey": "{{aws_secret_key}}",
"region": "sa-east-1",
"queueUrl": "https://sqs.sa-east-1.amazonaws.com/123456789012/orders-queue",
"receiptHandle": "{{messages[0].ReceiptHandle}}"
}
}
},
{
"id": "message_3",
"type": "message",
"position": { "x": 1700, "y": 50 },
"data": {
"label": "Sucesso",
"parameters": {
"message": "✅ Pedido {{order.orderId}} processado e removido da fila!"
}
}
},
{
"id": "message_4",
"type": "message",
"position": { "x": 900, "y": 150 },
"data": {
"label": "Fila Vazia",
"parameters": {
"message": "📭 Nenhum pedido pendente no momento"
}
}
},
{
"id": "end_1",
"type": "end",
"position": { "x": 1900, "y": 100 },
"data": { "label": "Fim" }
}
],
"edges": [
{ "source": "start_1", "target": "message_1" },
{ "source": "message_1", "target": "sqs_receive_1" },
{ "source": "sqs_receive_1", "target": "condition_1" },
{ "source": "condition_1", "target": "variable_1", "label": "true" },
{ "source": "condition_1", "target": "message_4", "label": "false" },
{ "source": "variable_1", "target": "message_2" },
{ "source": "message_2", "target": "delay_1" },
{ "source": "delay_1", "target": "sqs_delete_1" },
{ "source": "sqs_delete_1", "target": "message_3" },
{ "source": "message_3", "target": "end_1" },
{ "source": "message_4", "target": "end_1" }
]
}
Saída esperada:
Sistema: 🔄 Worker de pedidos iniciado...
Sistema: 📦 Processando pedido ORD-2025-001
💰 Valor: R$ 250.00
👤 Cliente: José Roberto
Sistema: ✅ Pedido ORD-2025-001 processado e removido da fila!
Exemplo 2: Worker com Tratamento de Erro
Objetivo: Deletar apenas se processamento for bem-sucedido
JSON para Importar
{
"name": "Worker com Tratamento de Erro",
"nodes": [
{
"id": "start_1",
"type": "start",
"position": { "x": 100, "y": 100 },
"data": { "label": "Início" }
},
{
"id": "sqs_receive_1",
"type": "aws_sqs",
"position": { "x": 300, "y": 100 },
"data": {
"label": "Receber Mensagem",
"parameters": {
"operation": "receiveMessages",
"accessKeyId": "{{aws_access_key}}",
"secretAccessKey": "{{aws_secret_key}}",
"region": "us-east-1",
"queueUrl": "{{worker_queue_url}}",
"maxMessages": 1,
"visibilityTimeout": 120
}
}
},
{
"id": "variable_1",
"type": "variable",
"position": { "x": 500, "y": 100 },
"data": {
"label": "Parse Body",
"parameters": {
"variable": "messageBody",
"value": "{{messages[0].Body}}"
}
}
},
{
"id": "condition_1",
"type": "condition",
"position": { "x": 700, "y": 100 },
"data": {
"label": "Validar Dados",
"parameters": {
"variable": "messageBody.orderId",
"operator": "exists",
"value": "true"
}
}
},
{
"id": "message_1",
"type": "message",
"position": { "x": 900, "y": 50 },
"data": {
"label": "Processar",
"parameters": {
"message": "✅ Dados válidos - processando..."
}
}
},
{
"id": "sqs_delete_1",
"type": "aws_sqs",
"position": { "x": 1100, "y": 50 },
"data": {
"label": "Deletar (Sucesso)",
"parameters": {
"operation": "deleteMessage",
"accessKeyId": "{{aws_access_key}}",
"secretAccessKey": "{{aws_secret_key}}",
"region": "us-east-1",
"queueUrl": "{{worker_queue_url}}",
"receiptHandle": "{{messages[0].ReceiptHandle}}"
}
}
},
{
"id": "message_2",
"type": "message",
"position": { "x": 1300, "y": 50 },
"data": {
"label": "Confirmar Sucesso",
"parameters": {
"message": "✅ Processado e removido da fila!"
}
}
},
{
"id": "message_3",
"type": "message",
"position": { "x": 900, "y": 150 },
"data": {
"label": "Erro Validação",
"parameters": {
"message": "❌ Dados inválidos - mensagem volta para fila após timeout"
}
}
},
{
"id": "end_1",
"type": "end",
"position": { "x": 1500, "y": 100 },
"data": { "label": "Fim" }
}
],
"edges": [
{ "source": "start_1", "target": "sqs_receive_1" },
{ "source": "sqs_receive_1", "target": "variable_1" },
{ "source": "variable_1", "target": "condition_1" },
{ "source": "condition_1", "target": "message_1", "label": "true" },
{ "source": "condition_1", "target": "message_3", "label": "false" },
{ "source": "message_1", "target": "sqs_delete_1" },
{ "source": "sqs_delete_1", "target": "message_2" },
{ "source": "message_2", "target": "end_1" },
{ "source": "message_3", "target": "end_1" }
]
}
Saída esperada (sucesso):
Sistema: ✅ Dados válidos - processando...
Sistema: ✅ Processado e removido da fila!
Saída esperada (erro):
Sistema: ❌ Dados inválidos - mensagem volta para fila após timeout
Resposta do Node
{
"success": true,
"message": "Message deleted successfully"
}
Fluxo: Receive → Process → Delete
┌─────────────────────────────────────────────┐
│ 1. receiveMessage() │
│ → Mensagem fica invisível │
│ → Retorna ReceiptHandle │
└─────────────────┬───────────────────────────┘
↓
┌─────────────────────────────────────────────┐
│ 2. Processar mensagem │
│ → Validar dados │
│ → Executar lógica de negócio │
│ → Salvar resultados │
└─────────────────┬───────────────────────────┘
↓
┌───────┴────────┐
│ Sucesso? │
└───────┬────────┘
Sim ↓ ↓ Não
┌────────────────┐ ┌──────────────────────┐
│ 3. deleteMessage│ │ Não deletar │
│ (ReceiptHandle)│ │ → Volta após timeout │
└────────────────┘ └──────────────────────┘
↓
┌─────────────────────────────────────────────┐
│ Mensagem REMOVIDA permanentemente │
└─────────────────────────────────────────────┘
Erros Comuns
ReceiptHandle Inválido
Erro: ReceiptHandleIsInvalid
Causa: Handle expirou após visibility timeout
Solução: Aumente visibilityTimeout ou processe mais rápido
Mensagem Não Existe
Erro: Message does not exist
Causa: Mensagem já foi deletada ou expirou
Solução: Verifique se não está deletando duplicado
Fila Não Encontrada
Erro: AWS.SimpleQueueService.NonExistentQueue
Causa: queueUrl incorreta
Solução: Verifique URL da fila
Boas Práticas
✅ SIM:
- Delete APENAS após processamento bem-sucedido
- Salve ReceiptHandle ao receber mensagem
- Configure visibilityTimeout > tempo processamento
- Implemente DLQ para mensagens problemáticas
- Use try-catch ao redor do delete
- Valide dados ANTES de deletar
- Log antes de deletar (auditoria)
- Configure maxReceiveCount apropriado
❌ NÃO:
- Não delete antes de processar completamente
- Não delete se validação falhou
- Não use MessageId (use ReceiptHandle)
- Não delete sem try-catch
- Não ignore erros de deleção
- Não reutilize ReceiptHandle expirado
- Não delete sem confirmar sucesso
Padrão Recomendado
try {
// 1. Receive
const result = await receiveMessages();
const message = result.messages[0];
const receiptHandle = message.ReceiptHandle;
// 2. Process
const data = JSON.parse(message.Body);
await processOrder(data);
// 3. Delete (apenas se sucesso)
await deleteMessage({ receiptHandle });
} catch (error) {
// Não delete - mensagem volta para fila
console.error('Processing failed:', error);
// Após maxReceiveCount tentativas → DLQ
}
Dicas
💡 Idempotência: Prepare-se para processar a mesma mensagem múltiplas vezes
💡 Auditoria: Log messageId antes de deletar para rastreamento
💡 Timeout: visibility > tempo de processamento + margem de segurança
💡 DLQ: Configure para capturar mensagens que falham repetidamente
💡 Batch Delete: Use deleteMessageBatch() para deletar múltiplas (até 10)
Próximo Node
→ SQS SEND - Enviar mensagem para fila → SQS RECEIVE - Receber mensagens da fila → SNS PUBLISH - Publicar em tópico SNS