Проверьте полезную нагрузку TypeForm Webhook в узле - PullRequest
0 голосов
/ 15 мая 2019

Я установил Typeform webhook , и он работает хорошо.

Теперь я пытаюсь защитить его, но я застрял в Проверке полезной нагрузки из секции Typeform .

Я адаптировал описанные шаги и пример Ruby (и пример PHP , который мне отправил справочный центр Typeform) в узел (Метеор):

const crypto = require('crypto');

function post() {
  const payload = this.bodyParams;
  const stringifiedPayload = JSON.stringify(payload);

  const secret = 'the-random-string';

  const receivedSignature = lodash.get(request, 'headers.typeform-signature', '');

  const hash = crypto
    .createHmac('sha256', secret)
    .update(stringifiedPayload, 'binary')
    .digest('base64');
  const actualSignature = `sha256=${hash}`;

  console.log('actualSignature:', actualSignature);
  console.log('receivedSignature:', receivedSignature);

  if (actualSignature !== receivedSignature) {
    return { statusCode: 200 };
  }

  // .. continue ..
});

Но actualSignature и receivedSignature никогда не совпадают, я получаю результаты типа:

actualSignature: sha256=4xe1AF0apjIgJNf1jSBG+OFwLYZsKoyFBOzRCesXM0g=
receivedSignature: sha256=b+ZdBUL5KcMAjITxkpzIFibOL1eEtvN84JhF2+schPo=

Почему это может быть?

1 Ответ

1 голос
/ 18 июля 2019

Вам необходимо использовать необработанный двоичный запрос, он указан в документации здесь

Используя алгоритм HMAC SHA-256, создайте хеш (с помощью create_token в качестве ключа) всей полученной полезной нагрузки в двоичном виде.

Вот пример использования промежуточного программного обеспечения express и body-parser

const crypto = require('crypto');
const express = require("express");
const bodyParser = require('body-parser');

const TYPEFORM_SECRET = 'your-secret';

const app = express();
const port = 3000;

app.use(bodyParser.raw({ type: 'application/json' }));

app.post(`/webhook`, (req, res) => {
  const expectedSig = req.header('Typeform-Signature');

  const hash = crypto.createHmac('sha256', TYPEFORM_SECRET)
    .update(req.body)
    .digest('base64');

  const actualSig = `sha256=${hash}`;

  if (actualSig !== expectedSig) {
    // invalid request
    res.status(403).send();
    return;
  }

  // successful

  res.status(200).send();
});

app.listen(port, () => {
  console.log(`listening on port ${port}!`);
});
...