{
  "name": "Вебхук оплаты: проверка подписи и защита от повторов",
  "nodes": [
    {
      "parameters": {
        "content": "## Приём уведомления об оплате\nСверяет HMAC-подпись, сразу отвечает 200 (или 401), отсекает повторную доставку того же order_id, отмечает заказ в таблице и пишет покупателю.\n\nПосле импорта: секрет из кабинета платёжного сервиса в узле «Подпись», правило склейки строки — по его документации; таблица и Gmail. Рабочий адрес появится после публикации.",
        "width": 560,
        "height": 230
      },
      "id": "2ee4c148-d9a9-55ac-a68e-2a07f0569164",
      "name": "Заметка 890b83",
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        -40,
        -280
      ]
    },
    {
      "parameters": {
        "httpMethod": "POST",
        "path": "payment",
        "responseMode": "responseNode",
        "options": {}
      },
      "id": "4ec90246-06c1-5ac1-a345-e315aac35390",
      "name": "Вебхук",
      "type": "n8n-nodes-base.webhook",
      "typeVersion": 2,
      "position": [
        0,
        0
      ],
      "webhookId": "47512390-8e5d-5577-840a-ef7e7ea4930f"
    },
    {
      "parameters": {
        "action": "hmac",
        "type": "SHA256",
        "value": "={{ $json.body.order_id }}:{{ $json.body.amount }}:{{ $json.body.status }}",
        "dataPropertyName": "expected",
        "secret": "ВАШ_СЕКРЕТ_ИЗ_КАБИНЕТА"
      },
      "id": "04a13125-d40f-5b4e-a436-a4f8ff76021b",
      "name": "Подпись",
      "type": "n8n-nodes-base.crypto",
      "typeVersion": 1,
      "position": [
        220,
        0
      ]
    },
    {
      "parameters": {
        "conditions": {
          "options": {
            "caseSensitive": true,
            "leftValue": "",
            "typeValidation": "loose",
            "version": 2
          },
          "conditions": [
            {
              "id": "bd79613a-2653-5aad-832d-e3323ed5d4a2",
              "leftValue": "={{ $json.expected }}",
              "operator": {
                "type": "string",
                "operation": "equals"
              },
              "rightValue": "={{ $json.body.signature }}"
            },
            {
              "id": "868b7943-b810-5912-8cc4-270b121425f9",
              "leftValue": "={{ $json.body.order_id }}",
              "operator": {
                "type": "string",
                "operation": "exists",
                "singleValue": true
              }
            }
          ],
          "combinator": "and"
        }
      },
      "id": "69ebc5a0-458f-5b43-944e-71e7b21fdd11",
      "name": "Подпись сошлась?",
      "type": "n8n-nodes-base.if",
      "typeVersion": 2.2,
      "position": [
        440,
        0
      ]
    },
    {
      "parameters": {
        "respondWith": "noData",
        "options": {
          "responseCode": 200
        }
      },
      "id": "d470a9d1-c473-511b-a7ab-611d3fb57371",
      "name": "Ответ 200",
      "type": "n8n-nodes-base.respondToWebhook",
      "typeVersion": 1.1,
      "position": [
        660,
        -100
      ]
    },
    {
      "parameters": {
        "respondWith": "noData",
        "options": {
          "responseCode": 401
        }
      },
      "id": "c3282488-5255-594f-8f55-f6e5d6f87454",
      "name": "Ответ 401",
      "type": "n8n-nodes-base.respondToWebhook",
      "typeVersion": 1.1,
      "position": [
        660,
        120
      ]
    },
    {
      "parameters": {
        "operation": "removeItemsSeenInPreviousExecutions",
        "logic": "removeItemsWithAlreadySeenKeyValues",
        "dedupeValue": "={{ $json.body.order_id }}",
        "options": {}
      },
      "id": "9d047347-8569-582f-9a48-7e07b2b8c144",
      "name": "Без повторов",
      "type": "n8n-nodes-base.removeDuplicates",
      "typeVersion": 2,
      "position": [
        880,
        -100
      ]
    },
    {
      "parameters": {
        "operation": "update",
        "documentId": {
          "__rl": true,
          "mode": "url",
          "value": "https://docs.google.com/spreadsheets/d/ZAMENITE_NA_ID_SVOEY_TABLICY/edit"
        },
        "sheetName": {
          "__rl": true,
          "mode": "name",
          "value": "Заказы"
        },
        "columns": {
          "mappingMode": "defineBelow",
          "value": {
            "order_id": "={{ $json.body.order_id }}",
            "status": "оплачен",
            "paid_at": "={{ $now.toISO() }}"
          },
          "matchingColumns": [
            "order_id"
          ],
          "schema": [
            {
              "id": "order_id",
              "displayName": "order_id",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "status",
              "displayName": "status",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "paid_at",
              "displayName": "paid_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            }
          ]
        },
        "options": {}
      },
      "id": "aad6c665-336b-5f1c-a515-9ce3fa79dfa1",
      "name": "Отметить оплату",
      "type": "n8n-nodes-base.googleSheets",
      "typeVersion": 4.5,
      "position": [
        1100,
        -100
      ]
    },
    {
      "parameters": {
        "sendTo": "={{ $('Вебхук').item.json.body.email }}",
        "subject": "=Оплата заказа {{ $('Вебхук').item.json.body.order_id }} получена",
        "emailType": "text",
        "message": "=Здравствуйте! Мы получили оплату {{ $('Вебхук').item.json.body.amount }} ₽ по заказу {{ $('Вебхук').item.json.body.order_id }}. Сообщим, когда отправим.",
        "options": {}
      },
      "id": "373d9fdc-32ac-58a1-868a-9024d3161ce3",
      "name": "Письмо покупателю",
      "type": "n8n-nodes-base.gmail",
      "typeVersion": 2.1,
      "position": [
        1320,
        -100
      ]
    }
  ],
  "connections": {
    "Вебхук": {
      "main": [
        [
          {
            "node": "Подпись",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Подпись": {
      "main": [
        [
          {
            "node": "Подпись сошлась?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Подпись сошлась?": {
      "main": [
        [
          {
            "node": "Ответ 200",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Ответ 401",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Ответ 200": {
      "main": [
        [
          {
            "node": "Без повторов",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Без повторов": {
      "main": [
        [
          {
            "node": "Отметить оплату",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Отметить оплату": {
      "main": [
        [
          {
            "node": "Письмо покупателю",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  },
  "settings": {
    "executionOrder": "v1"
  },
  "pinData": {},
  "active": false,
  "meta": {
    "templateCredsSetupCompleted": false,
    "source": "promtbaza.com/voprosy/shablony-n8n"
  }
}