I have followed the steps given in https://sendgrid.com/docs/for-developers/tracking-events/getting-started-event-webhook-security-features/ for PHP and used library mentioned in https://github.com/sendgrid/sendgrid-php/tree/main/lib/eventwebhook similarly checked unittest https://github.com/sendgrid/sendgrid-php/blob/main/test/unit/EventWebhookTest.php for event signature verification
$timestamp = $req->header("X-Twilio-Email-Event-Webhook-Timestamp");
$signature = $req->header("X-Twilio-Email-Event-Webhook-Signature");
$verifycationKey = "<Verification Key>";
$body = \json_encode($req->all())."\r\n";
\Log::info("+++++++++++++++++++");
\Log::info($body);
\Log::info($timestamp);
\Log::info($signature);
$event = new EventWebhook;
$publicKey = $event->convertPublicKeyToECDSA($verifycationKey);
\Log::info(serialize($publicKey));
$flag =$event->verifySignature($publicKey, $body, $signature, $timestamp);
\Log::info("flag====> ".$flag);
\Log::info("+++++++++++++++++++");
We've seen a similar issue in our nodejs library recently: https://github.com/sendgrid/sendgrid-nodejs/issues/1238
Is this a multi-event webhook? If so, a carriage return and newline (rn) needs to be included between every event in the body. Example: https://github.com/sendgrid/sendgrid-nodejs/pull/1271/files#diff-570eee91600a9234a175a0acce452638ee2c7cc583be1a4aa75eb35ca8b9500cR48
Yes we are having multi-event webhook. As per your comment we have modified the code as follows still not luck.
`
$timestamp = $req->header("X-Twilio-Email-Event-Webhook-Timestamp");
$signature = $req->header("X-Twilio-Email-Event-Webhook-Signature");
$verifycationKey = "
$body = json_encode($req->all());
$body = str_replace("},{", "},rn{",$body)."rn";
Log::info("+++++++++++++++++++");
Log::info($body);
Log::info($timestamp);
Log::info($signature);
$event = new EventWebhook;
$publicKey = $event->convertPublicKeyToECDSA($verifycationKey);
Log::info(serialize($publicKey));
$flag =$event->verifySignature($publicKey, $body, $signature, $timestamp);
Log::info("flag====> ".$flag);
Log::info("+++++++++++++++++++");
`
@iprashant have you tried with the raw body?
$body = $request->getContent()
$body = str_replace("},{", "},\r\n{",$body)."\r\n";
Hi Shwetha,
I have used PHP file_get_contents('php://input'); still no luck.
Thanks,
OK, we have an internal ticket to investigate the multi-event webhook scenario. Marking this as a bug in the meantime.
This issue has been added to our internal backlog to be prioritized. Pull requests and +1s on the issue summary will help it move up the backlog.
This replacement worked for me on multi-event payloads instead of the one above:
$bodyContent = str_replace(
"},\n{", // The raw string comes in with newlines in this spot
"},\r\n{",
$body // $request->getContent() can be used here for Laravel apps
)."\r\n";
Thank you for taking the time to share your solution @peter-at-bpt!
Most helpful comment
This replacement worked for me on multi-event payloads instead of the one above: