บทความทั้งหมด
วิธีทดสอบ Mailgun Webhook บน localhost
Mailgunemail webhooksHMAC verificationlocalhost

วิธีทดสอบ Mailgun Webhook บน localhost

เพื่อทดสอบ Mailgun เว็บฮุคบนเครื่องในท้องถิ่น เปิดโปงผู้ดูแลท้องถิ่นของคุณด้วย npx portpreview PORTตั้งค่าจุดสิ้นสุด HTTPS ที่มีผลตามความต้องการ Mailgun และตรวจสอบลายเซ็น HMAC-SHA256 ของเหตุการณ์

สิ่งที่ Mailgun รายงานเว็บฮุค

Mailgun ส่ง HTTP หรือ HTTPS POST ที่มีการโหลด Json เมื่อเหตุการณ์ตั้งค่าเกิดขึ้น ชนิดของเหตุการณ์ปัจจุบัน accepted. delivered. temporary_fail. permanent_fail. opened. clickedการร้องเรียนแบบสแปม และการระบุตัวตน เหตุการณ์ที่ขึ้นอยู่กับการติดตาม จะปรากฏขึ้นเมื่อเปิดใช้งานการติดตามที่สอดคล้องกันเท่านั้น

แบบปัจจุบันส่งอีเมลเว็บฮุค signature วัตถุอยู่ด้านข้าง event-dataสืบค้นเมื่อเกิดเหตุการณ์ event. id. timestampหัวจดหมาย, ข้อมูลผู้รับ, ป้ายกํากับ, และรายละเอียดการส่ง ขึ้นอยู่กับประเภทของเหตุการณ์ รหัสกับสนามเอกสาร และอดทนกับการขาดคุณสมบัติ Mailgun อย่างเป็นทางการ ตัวอย่างการโหลด การรักษาที่ดีที่สุดสําหรับการทดสอบสัญญา

อย่าสับสน Mailgun Send เว็บฮุค Mailgun แจ้งเตือน แจ้งเตือนจะใช้คีย์อื่น ๆ และลงนามทั้งร่างกาย POS เป็น X-Sign ส่วนหัว นําทางนี้ ใช้ครอบคลุมการส่ง webgs: ช่องข้อมูลลายเซ็นใน partload และบัญชีกุญแจสําหรับใช้เซ็นบนเว็บ.

1. สร้างจุดปลายภายใน Mailgun

ต่างกับแผนการที่ลงนามในร่าง Json, Mailgun Send บันทึกการคํานวณ ใช้ลายเซ็นของวัตถุ เวลาและสัญลักษณ์ มาตรฐาน เจ สัน ตัวจัดการ Express ต่อไปนี้ จะยืนยันข้อมูล HMAC, ทําการตรวจสอบซ้ําอีกครั้ง และยอมรับเหตุการณ์ได้

import crypto from 'node:crypto';
import express from 'express';

const app = express();
app.use(express.json({ limit: '1mb' }));

function verifyMailgunSignature({ timestamp, token, signature }) {
  if (!timestamp || !token || !signature) return false;

  const expected = crypto
    .createHmac('sha256', process.env.MAILGUN_WEBHOOK_SIGNING_KEY)
    .update(String(timestamp) + String(token))
    .digest('hex');

  const expectedBytes = Buffer.from(expected, 'hex');
  const actualBytes = Buffer.from(String(signature), 'hex');
  return expectedBytes.length === actualBytes.length &&
    crypto.timingSafeEqual(expectedBytes, actualBytes);
}

app.post('/webhooks/mailgun', async (req, res) => {
  const signing = req.body?.signature;
  const event = req.body?.['event-data'];

  if (!signing || !event || !verifyMailgunSignature(signing)) {
    return res.status(406).send('invalid webhook');
  }

  const ageSeconds = Math.abs(Date.now() / 1000 - Number(signing.timestamp));
  if (!Number.isFinite(ageSeconds) || ageSeconds > 15 * 60) {
    return res.status(406).send('stale webhook');
  }

  await acceptOnce({
    eventId: event.id,
    replayToken: signing.token,
    payload: event,
  });
  return res.sendStatus(200);
});

app.listen(3000);

หน้าต่าง 15 นาทีนี้ เป็นข้อกําหนดการใช้งาน ไม่ใช่ Mailgun- mmanded value Mailgun ขอแนะนําให้ตรวจสอบว่า timetamp ไม่ไกลจากเวลาปัจจุบันมาก แต่เตือนไม่ให้ก้าวร้าวเกินไป เนื่องจากการส่งมอบสามารถล่าช้าได้ เลือกหน้าต่างที่ตรงกับความต้องการการเข้าคิวและเรียกคืนเหตุการณ์, เฝ้าดูการปฏิเสธที่ถูกต้อง, และปรับแต่งมันอย่างจงใจ

เก็บ Webhook Signing Key ไว้ในโปรแกรมจัดการหรือตัวแปรแวดล้อมที่ไม่อยู่ในแหล่งควบคุม Mailgun ส่วนเสริมการจับเว็บ กําหนดการคํานวณที่แน่นอน: conternate timetamp และสัญลักษณ์ที่ไม่มีตัวแบ่ง คํานวณ HMAC-SHA256 โดยใช้ Webhook Signing Key และเปรียบเทียบการย่อยค่า xxdecimal กับ signature.

2. เปิดโปงเครื่องในท้องถิ่นเหนือ HTTPs

ด้วยโปรแกรมที่รอฟังเมื่อพอร์ต 3000 ให้ทํางาน:

npx portpreview 3000

เพิ่มเส้นทางท้องถิ่นไปยังแหล่งกําเนิดของ HTTPs ตัว อย่าง เช่น:

https://example.portpreview.dev/webhooks/mailgun

ออกจากทั้งโปรแกรมและอุโมงค์ที่กําลังทํางานอยู่ระหว่างการทดสอบ Mailgun ต้องการที่อยู่ URL ที่เข้าถึงได้อย่างเปิดเผย localhostPortPreview ทําการยกเลิก HTTPs และส่งต่อคําขอไปยังพอร์ตท้องถิ่นของคุณ

3. ปรับแต่งที่อยู่ URL ของเหตุการณ์ Mailgun

Mailgun รองรับการปรับแต่งเว็บฮุคระดับบัญชีและโดเมนของโดเมน จุดปลายของบัญชีสามารถรับเหตุการณ์ต่างๆ ไปทั่วโดเมน และค่าเศษส่วนที่สืบทอดมา ส่วนจุดปลายของโดเมนนั้นใช้ได้เฉพาะกับโดเมนเท่านั้น แต่ละประเภทของเหตุการณ์ถูกปรับแต่งเป็นรายบุคคล และสามารถมีที่อยู่ URL ได้ถึง 3 ที่ เลือกขอบเขตที่แคบที่สุดที่ตรงกับโปรแกรมของคุณ

  1. เปิดพื้นที่เว็บฮุกสําหรับบัญชีที่ตั้งใจหรือส่งโดเมน
  2. เลือกประเภทของเหตุการณ์ เช่น delivered หรือ permanent_fail.
  3. เพิ่มเต็มPortPreviewจุดปลาย HTTPs
  4. ทําซ้ําสําหรับแต่ละประเภทของผู้ดูแลของคุณที่รองรับ
  5. ส่งข้อความหรือข้อความจริง และตรวจสอบการร้องขอภายในและปูมบันทึกของโปรแกรม

Mailgun ลดความเปรียบต่างของที่อยู่ URL สําหรับเหตุการณ์เดียวกัน เมื่อมีการปรับแต่งทั้งบัญชีและระดับโดเมนแล้ว แต่ที่อยู่ URL ที่แตกต่างกันนั้น สามารถรับสําเนาได้แต่ละคน มรดกของผู้ปกครอง สามารถทําให้การส่งมอบ มีจุดสิ้นสุดที่แตกต่างกันหลายจุด จง ทบทวน เจ้า หน้าที่ กฎการปรับแต่ง ก่อนจะส่งของเพิ่มทุก ๆ ที่เพื่อการบูรณะ

ลายเซ็น Mailgun ทํางานอย่างไร

เดอะ signature วัตถุบรรจุ:

  • timestampเวลา Uniix ในวินาที.
  • tokenสุ่มสร้างเชือก 50 แท่ง
  • signatureการย่อย HMAC
  • parent-signatureนําเสนอสําหรับเหตุการณ์จาก subaccount, อนุญาตให้ถูกต้องกับความสัมพันธ์หลักบัญชีที่บรรยายโดยจดหมาย.

สําหรับลายเซ็นดิจิตัลปกติ HMAC-SHA256(signingKey, timestamp + token)ไม่มีตัวแบ่ง และ event-data Json ไม่ได้เป็นส่วนหนึ่งของการคํานวณนี้ Mailgun Send เทียบการถอดรหัสข้อมูล bytes ด้วยฟังก์ชันปลอดภัยเวลา หลังจากการตรวจสอบความยาวเท่ากัน ธรรมดา === การเปรียบเทียบนั้นง่ายกว่า แต่การเปรียบเทียบเวลาที่ปลอดภัย เป็นค่าปริยายของการผลิตที่ปลอดภัยกว่า

HMAC ตัวจริง พิสูจน์ว่าบุคคลที่ถือกุญแจการเซ็นนั้น ทําให้เกิดลายเซ็น ไม่ ได้ พิสูจน์ ว่า การ ส่ง นี้ ไม่ ได้ รับ การ แก้ไข.จดหมายโดย เฉพาะ อย่าง ยิ่ง ควร เสนอ แนะ ให้ เก็บ เหรียญ นั้น ไว้ และ ปฏิเสธ คํา ขอ ต่อ จาก นั้น ด้วย สัญลักษณ์ อย่าง เดียว กัน. การตรวจอายุของเวลาจํากัด ว่าความต้องการที่จับได้ยังคงมีประโยชน์อยู่นานแค่ไหน ใช้ทั้งตัวควบคุม: เงื่อนไขเฉพาะสําหรับการเล่นซ้ํา และหน้าต่างเวลาที่เหมาะสมสําหรับความสด

ความซับซ้อนทั้งการส่งและส่งผลกระทบ

เก็บเงื่อนไขการไม่ซ้ํากันสองตัว: อันแรกสําหรับลายเซ็นและหนึ่งสําหรับ Mailgun event-data.idสัญลักษณ์นี้จับการลงนามในชื่อเดียวกัน ID ของเหตุการณ์ที่ปกป้องตรรกะทางธุรกิจ ถ้าเหตุการณ์เดียวกันปรากฏในบริบทอื่นที่ถูกต้อง ชื่อแฟ้มโดยผู้ให้บริการและบัญชีผู้ใช้ หรือสภาพแวดล้อม

async function acceptOnce({ eventId, replayToken, payload }) {
  await db.transaction(async (tx) => {
    const tokenWasNew = await tx.webhookTokens.insertIfAbsent({
      provider: 'mailgun',
      token: replayToken,
    });
    if (!tokenWasNew) return;

    const eventWasNew = await tx.webhookEvents.insertIfAbsent({
      provider: 'mailgun',
      eventId,
      receivedAt: new Date(),
    });
    if (!eventWasNew) return;

    await tx.jobs.enqueue({
      type: 'process-mailgun-event',
      payload,
    });
  });
}

ย้อนกลับการแทรก-หาก-เปิดใช้งานด้วยดัชนีฐานข้อมูลที่ไม่ซ้ํากัน; การอ่านตามด้วยการแทรก คือ การพิมพ์เชื้อชาติภายใต้การส่งซ้ํา เชื่อมโยงบันทึกการปลดระวางและตําแหน่งงานตามทฤษฎี ดัง นั้น จง ยอม รับ อย่าง รวด เร็ว และ ให้ พนักงาน ปรับ เปลี่ยน สถานะ ข่าวสาร, เตือน ให้ เกิด สัญญาณ เตือน, หรือ ทํา ให้ เกิด การ ประสาน เสียง กัน. ดู ความพยายามและการจํากัดความ สําหรับตัวเลือกอื่น ๆ เมื่อคิวและฐานข้อมูลธุรกิจไม่สามารถใช้ร่วมกันได้

Mailgun รหัสตอบโต้และพยายามอีกครั้ง

Mailgun เอกสารเกี่ยวกับเว็บฮุคปัจจุบัน ให้ผล 3 อย่างที่สําคัญ:

  • สําเร็จ 200 ครั้ง: Mailgun ถือเว็บฮุค POST ว่าประสบความสําเร็จและไม่ลองใหม่
  • 406 ไม่ยอมรับ: พ.ศ. Mailgun ปฏิบัติกับ POST ถูกปฏิเสธ และไม่ลองใหม่
  • รหัสอื่น: สําหรับ webhooks อื่นนอกเหนือจากการแจ้งเตือนการส่งมอบ Mailgun retricies มากกว่า 8 ชั่วโมงที่ 5 นาที 10 นาที 15 นาที 1 ชั่วโมง 2 ชั่วโมง และ 4 ชั่วโมง

ข้อยกเว้นการแจ้งเตือนการส่ง: อย่าสัญญาว่าเหตุการณ์ทุกประเภท จะเป็นไปตามกําหนดการทั่วไป ตรวจสอบล่าสุด ตรวจหาเอกสารอัตโนมัติ เมื่อการส่งมอบ มีผลกระทบต่อการออกแบบของคุณ

ใช้ 406 เท่านั้นสําหรับการร้องขอที่คุณตั้งใจปฏิเสธอย่างถาวร เช่น ลายเซ็นไม่ถูกต้อง หรือเล่นนอกระบบอีกครั้ง ใช้ 500 หรือ 503 สําหรับฐานข้อมูลชั่วคราวและคิวล้มเหลว เพื่อให้ชนิดของเว็บฮุคที่เหมาะสมสามารถลองใหม่ ผลตอบแทน 200 หลังการยอมรับที่ทนทาน การส่งกลับ 200 ขณะเริ่มทํางานเบื้องหลังที่ยังไม่ได้ติดตาม สามารถสูญเสียเหตุการณ์ได้หากโพรเซสออกจากการทํางาน

การดักจับ Mailgun เว็บฮุคภายในเครื่อง

HMAC ที่คํานวณแล้วไม่เคยตรงกัน

ยืนยันว่าคุณกําลังใช้ Webhook Signing Keyกดปุ่ม API, รหัสผ่าน SMTP หรือปุ่ม แจ้งเตือน กําหนดเวลาและเวลาของออบเจกต์ของออบเจกต์ และสัญลักษณ์ที่ไม่มีตัวแยก ผลิต เฮก เซ เด ซิ มาล SHA-256 ขนาด เล็ก. ตรวจสอบด้วยว่าเฟรมของคุณยังไม่ได้เปลี่ยนชื่อความอิ่มตัว event-data สมบัติ; สัญลักษณ์วงเล็บหลีกเลี่ยงความผิดพลาดนั้น

ตัวจัดการรับข้อมูลฟอร์มแทน Json ปัจจุบัน

ตรวจสอบว่าคุณสมบัติ Mailgun and endpoint รุ่นใด ที่สร้างการร้องขอ อย่า นํา สิ่ง ที่ ได้ รับ ตก ทอด มา ใช้ ไป ใช้ ใน การ สอน ลูก ให้ รู้ จัก หนังสือ บันทึกเนื้อหาประเภท, ชื่อสนามด้านบน, และความยาวตัวที่อยู่ในการพัฒนา โดยไม่ต้องบันทึกเนื้อหาหรือความลับ, แล้วจัดทําสัญญาเอกสารสําหรับบัญชีผู้ใช้และส่วนผนวกของคุณ

จดหมายพยายามต่อไป

ระบุสถานะจริงที่ส่งไป ข้อยกเว้นหลังจากที่ทําฐานข้อมูลแล้ว อาจเปลี่ยนการตอบสนองเป็น 500 ซึ่งทําให้เกิดความพยายามอีกครั้ง นั่นคือเหตุผลว่าทําไมหมายเลขและเครื่องหมายที่แทรก ต้องมีลักษณะเฉพาะและทนทาน ถ้า คํา ร้อง ขอ นั้น ไม่ ได้ ผล อย่าง ถาวร ให้ กลับ มา 406; หาก เกิด ความ ล้ม เหลว ชั่ว คราว จง แก้ไข การ รับ ใช้ นั้น และ ยอม ให้ พฤติกรรม ที่ กลับ มา ทํา งาน อีก.

ไม่มีเหตุการณ์ใด ๆ ถึงเครื่องภายใน

ยืนยันที่อยู่ URL จะถูกแนบเข้ากับบัญชีหรือโดเมนที่ถูกต้อง และตรงกับชนิดของเหตุการณ์ที่แน่นอน A delivered ไม่ได้รับที่อยู่ URL opened เหตุการณ์ โปรดตรวจสอบว่า โพรเซสและอุโมงค์ภายในยังทํางานอยู่ และพาธที่ปรับแต่งไว้ /webhooks/mailgunทําตาม ปลั๊กอินดีบั๊กเว็บภายใน เพื่อแยกการปรับแต่งของผู้ให้บริการออกจาก routing และโปรแกรมผิดพลาด

รายการรักษาความปลอดภัย

  • ตรวจสอบ HMAC ก่อนการเชื่อใจหรือทําปูมบันทึก event-data.
  • เก็บกุญแจไว้ในร้านลับ และหมุนมันผ่านระบบควบคุม อย่าเปิดเผยมันในรหัสลูกค้า
  • ใช้การเปรียบเทียบการประหยัดเวลาแบบปลอดภัย, ข้อกําหนดการจับเวลา, และเงื่อนไขที่ทนทานกับเครื่องหมาย
  • ตรวจสอบความถูกต้องของเหตุการณ์ประเภทและต้องการช่องข้อมูล ก่อนที่จะทําการขยายภาพ รักษาที่อยู่ผู้รับ, หัวข้อ, ที่อยู่ URL เก็บ, และตัวแปรผู้ใช้เป็นข้อมูลละเอียดอ่อน
  • ยอมรับเฉพาะ POST, ขนาดตัวฝา, ใช้ HTTPs, และอัตรา-limit ล้มเหลวโดยไม่ต้องป้องกันการเกิดขึ้นอีกที่ชอบธรรม Mailgun
  • อย่า เปิดโปง โฆษณา ใน ท้อง ถิ่น หรือ จุด จบ ของ การ ดีบั๊ก โดย ทาง แหล่ง ที่ มา ชั่ว คราว ของ ประชาชน.
  • เมื่อการทดสอบสิ้นสุดลง ให้ลบที่อยู่ URL ชั่วคราวออก และปรับแต่งจุดสิ้นสุดการผลิตที่เสถียร

Mailgun นอกจากนี้ยังทําเอกสารเพิ่มเติม ใบรับรองไคลเอนต์ TLS บนการร้องขอเว็บฮุก เมื่อเซิร์ฟเวอร์ของคุณมี TLS ที่ถูกต้อง ซึ่งสามารถให้สิทธิ์ในการรับข้อมูลระดับการขนส่งได้ แต่ก็ไม่ได้ทําการแทนที่การตรวจสอบ HMAC, การเล่นซ้ํา, และการอนุมัติจากโปรแกรม เลเยอร์ควบคุมตามรูปแบบภัยคุกคามของคุณ

ทดสอบการยอมรับ

  1. ส่งสัญญารับรองที่ถูกต้อง และยืนยันเหตุการณ์ที่ทนทานหนึ่งกับ 200 การตอบสนอง
  2. เปลี่ยนตั๋วโดยไม่เปลี่ยนลายเซ็น และยืนยันหมายเลข 46 โดยไม่เขียนเหตุการณ์
  3. เล่นซ้ําร่างกายที่ถูกต้องเป๊ะ และยืนยันว่าไม่มีงานที่สองหรือผลข้างเคียง
  4. ส่งลายเซ็นที่ถูกต้องด้วยนาฬิกาที่อยู่นอกหน้าต่างที่คุณปรับแต่งไว้ และตรวจสอบการปฏิเสธที่ตั้งใจไว้
  5. บังคับใช้ข้อผิดพลาดชั่วคราวในฐานข้อมูล โปรดยืนยันการตอบรับที่ไม่ใช่-200/NOn-406 แล้วเรียกคืนฐานข้อมูลและตรวจสอบการยอมรับที่ประสบความสําเร็จ
  6. การ ออก กําลัง กาย Mailgun ชนิด ของ เหตุ การณ์ แต่ ละ ชนิด เนื่อง จาก ทุ่ง นา ที่ ได้ รับ ภาระ และ การ ทดลอง ความ คาด หมาย ต่าง กัน.

เมื่อ ผ่าน การ ตรวจ เหล่า นั้น แล้ว จง ใช้ เส้น ทาง การ ตรวจ สอบ แบบ เดียว กัน และ การ ลด ความ เร็ว ใน การ ผลิต. สําหรับคําอธิบายการพึ่งพาผู้จัดหา การเปรียบเทียบ HMAC และการจัดการลับอ่าน คู่มือตรวจสอบลายเซ็นของเว็บ.

คำถามที่พบบ่อย

Mailgun จะส่งเว็บฮุกไปเครื่องในท้องถิ่นได้ไหม?
Mailgun ไม่สามารถเข้าถึงเครื่องภายในโดยตรง เรียกใช้ `npx portpreview PORT`, เพิ่มเส้นทางเว็บฮุคของคุณไปยังแหล่งกําเนิด HTTPS และปรับแต่งที่อยู่ URL ของสาธารณชนสําหรับแต่ละรายการที่ต้องการ Mailgun
ฉันจะตรวจสอบลายเซ็นเว็บฮุค Mailgun Send อย่างไร
เรียกค่าเวลาและลายเซ็นของออบเจกต์ของออบเจกต์ที่มีเครื่องหมาย HMAC-SHA256 คํานวณค่าย่อยของเลขฐานสิบหกโดยใช้ Webhook Signing Key และเปรียบเทียบมันกับลายเซ็นที่ให้มา โดยใช้ค่าเวลาที่มีความปลอดภัย
ฉันจะป้องกันยังไงจดหมายเว็บฮุค เล่นการโจมตี?
เก็บลายเซ็นแต่ละตัวไว้ภายใต้เงื่อนไขที่ไม่ซ้ํากัน และปฏิเสธเครื่องหมายที่เห็นอยู่แล้ว นอกจากนี้ยังบังคับใช้นโยบายเวลาที่เหมาะสม อนุญาตให้มีเวลาเพียงพอสําหรับการส่งมอบอย่างถูกต้อง และความต้องการดําเนินการของคุณ
Mailgun จะลองใหม่เมื่อไหร่
Mailgun ทํา 200 เป็นความสําเร็จ และ 406 เป็นการปฎิเสธอย่างถาวร สําหรับการตอบสนองอื่น ๆ เว็บฮุคอื่น ๆ นอกจากการแจ้งการส่งมอบจะใช้ระยะเวลาที่บันทึกไว้ในการพิมพ์กว่าแปดชั่วโมง ดังนั้นผู้ดูแลจะต้อง idemotent