C#
Проверка вебхуков
Проверьте подпись доставки, прежде чем доверять её содержимому.
Проверка доставки
using OpenEmail; var builder = WebApplication.CreateBuilder(args);var app = builder.Build();var secret = builder.Configuration["OPENEMAIL_WEBHOOK_SECRET"] ?? string.Empty; app.MapPost("/webhooks/openemail", async (HttpRequest request) =>{ using var reader = new StreamReader(request.Body); var payload = await reader.ReadToEndAsync(); try { var delivery = OpenEmailClient.VerifyWebhookSignature(payload, request.Headers["X-OpenEmail-Signature"], secret); app.Logger.LogInformation("{Type} {Id}", (string?)delivery["type"], (string?)delivery["id"]); return Results.NoContent(); } catch (OpenEmailWebhookException) { return Results.BadRequest(); }}); app.Run();OpenEmailClient.VerifyWebhookSignature() проверяет HMAC заголовка по метке времени и телу за постоянное время и возвращает событие как JsonObject. Второй аргумент содержит значение заголовка X-OpenEmail-Signature, а другие перегрузки принимают сами заголовки запроса. Секрет тот самый, который вернул client.Webhooks.CreateAsync().
Передавайте необработанное тело в точности таким, каким оно пришло. Тело, которое разобрали и закодировали заново, уже не совпадает со своей подписью.
Старые доставки
var payload = """{"id":"evt_1","type":"email.received"}"""; try{ OpenEmailClient.VerifyWebhookSignature(payload, "t=1767225600,v1=5f2d", "whsec_example", toleranceSeconds: 60);}catch (OpenEmailWebhookException error){ Console.WriteLine($"refused: {error.Message}");}Доставка старше пяти минут отклоняется, поэтому перехваченный запрос нельзя воспроизвести позже. toleranceSeconds: меняет эти пять минут, а ноль принимает доставку любого возраста.
- Отсутствующий или неверно составленный заголовок, несовпадающая подпись и слишком старая доставка вызывают
OpenEmailWebhookException. - После смены секрета доставка может нести больше одной подписи, и достаточно совпадения любой из них.
- Отвечайте статусом 2xx быстро. Доставка, получившая любой другой ответ, повторяется позже.