
Met de toename van e-mailgebruik in gereguleerde omgevingen, heb ik besloten dat het tijd is om een nieuw project te starten dat al deze elementen samenbrengt met codevoorbeelden over hoe de e-mailtekst en alle bijbehorende gegevens kunnen worden opgeslagen.
Ongeveer een jaar geleden schreef ik een blog over hoe kopieën van e-mails verkregen kunnen worden voor archivering en weergave, maar ik behandelde niet het daadwerkelijk opslaan van de e-mail of gerelateerde gegevens. Onlangs schreef ik een blog over het opslaan van alle gebeurtenisgegevens (d.w.z. wanneer de e-mail werd verzonden, geopend, geklikt, bounces, afmeldingen, enz.) van een e-mail voor auditdoeleinden, maar ik koos ervoor om geen ondersteunende code te maken.
Met de toename van e-mailgebruik in gereguleerde omgevingen, heb ik besloten dat het tijd is voor een nieuw project dat alles samenbrengt met codevoorbeelden over hoe de e-mailinhoud en alle bijbehorende gegevens kunnen worden opgeslagen. In het komende jaar zal ik aan dit project blijven werken met als doel een werkende opslag- en weergaveapplicatie te creëren voor gearchiveerde e-mails en alle loginformatie die door SparkPost wordt geproduceerd. SparkPost heeft geen systeem dat de e-mailinhoud archiveert, maar maakt het bouwen van een archiveringsplatform vrij eenvoudig.
In deze blogserie zal ik het proces beschrijven dat ik heb doorlopen om de e-mailinhoud op S3 (Amazon’s Simple Store Service) op te slaan en alle relevante loggegevens in MySQL voor eenvoudige kruisverwijzing. Voor productiesystemen voor archivering die robuuste databaseback-upstrategieën vereisen, overweeg een uitgebreide PostgreSQL back-up en herstelproces te implementeren om ervoor te zorgen dat uw archiefgegevens goed beschermd zijn. Uiteindelijk is dit het startpunt voor het bouwen van een applicatie waarmee gearchiveerde e-mails eenvoudig kunnen worden doorzocht en die e-mails samen met de gebeurtenis (log) gegevens worden weergegeven. De code voor dit project is te vinden in de volgende GitHub-repository: https://github.com/jeff-goldstein/PHPArchivePlatform
Deze eerste bijdrage van de blogserie gaat de uitdaging beschrijven en een architectuur voor de oplossing uitwerken. De rest van de blogs zal delen van de oplossing in detail uitwerken samen met codevoorbeelden.
De eerste stap in mijn proces was om uit te zoeken hoe ik een kopie van de naar de oorspronkelijke ontvanger verzonden e-mail kon verkrijgen. Om een kopie van de e-mailinhoud te verkrijgen, moet je ofwel:
De e-mailinhoud vastleggen voordat de e-mail wordt verzonden
De e-mailserver een kopie laten opslaan
De e-mailserver een kopie voor je laten maken voor opslag
Als de e-mailserver items toevoegt zoals linktracking of open tracking, kan je #1 niet gebruiken omdat het de open/klik trackingswijzigingen niet weergeeft.
Dat betekent dat de server de e-mail moet opslaan of op de een of andere manier een kopie van die e-mail aan je beschikbaar moet stellen voor opslag. Aangezien SparkPost geen opslagmechanisme voor e-mailinhoud heeft maar wel een manier heeft om een kopie van de e-mail te maken, zullen we SparkPost ons een duplicaat van de e-mail laten sturen om op S3 op te slaan.
Dit wordt gedaan met behulp van de Archive-functie van SparkPost. De Archive-functie van SparkPost geeft de afzender de mogelijkheid om SparkPost te vertellen een duplicaat van de e-mail naar een of meerdere e-mailadressen te sturen en dezelfde tracking- en open links te gebruiken als het origineel. SparkPost-documentatie definieert hun Archive-functie op de volgende manier:
Ontvangers in de archieflijst ontvangen een exacte kopie van het bericht dat naar het RCPT TO-adres is verzonden. In het bijzonder zullen alle gecodeerde links die bedoeld zijn voor de RCPT TO-ontvanger identiek zijn in de archiefberichten
De enige verschillen van de RCPT TO-e-mail zijn dat sommige headers anders zullen zijn, omdat het doeladres voor de archiverings-e-mail anders is, maar de inhoud van de e-mail zal een exacte kopie zijn!
Als je een diepere uitleg wilt, hier is een link naar de SparkPost-documentatie over het maken van duplicaten (of archief) exemplaren van een e-mail.
Terzijde, SparkPost stelt je eigenlijk in staat om e-mails te sturen naar cc, bcc en archive e-mailadressen. Voor deze oplossing richten we ons op de archive-adressen.
* Let op * Gearchiveerde e-mails kunnen ALLEEN worden gemaakt wanneer e-mails in SparkPost worden geïnjecteerd via SMTP!
Nu we weten hoe we een kopie van de oorspronkelijke e-mail kunnen verkrijgen, moeten we kijken naar de loggegevens die worden geproduceerd en enkele van de subtiele nuances binnen die gegevens. SparkPost houdt alles bij wat er op zijn servers gebeurt en biedt die informatie aan je aan in de vorm van boodschap-gebeurtenissen. Die gebeurtenissen worden 10 dagen lang op SparkPost opgeslagen en kunnen via een RESTful API message-events van de server worden gehaald, of je kunt SparkPost die evenementen naar elk gewenst aantal verzamelapplicaties laten pushen. Het push-mechanisme wordt gedaan via webhooks en in real-time uitgevoerd.
Momenteel zijn er 14 verschillende evenementen die zich kunnen voordoen met een e-mail. Hier is een lijst van de huidige evenementen:
Bounce
ClickDelay
Delivery
Generation Failure
Generation Rejection
Initial Open
InjectionLink Unsubscribe
List Unsubscribe
Open
Out of Band
Policy RejectionSpam Complaint
* Volg deze link voor een actuele referentiegids met een beschrijving van elke gebeurtenis samen met de gegevens die voor elke gebeurtenis worden gedeeld.
Elke gebeurtenis heeft talrijke velden die overeenkomen met het type gebeurtenis. Sommige velden zoals het transmission_id worden in elke gebeurtenis gevonden, maar andere velden kunnen specifieker voor de gebeurtenis zijn; bijvoorbeeld, alleen open- en klikgebeurtenissen hebben geotag-informatie.
Een zeer belangrijke boodschap-gebeurtevent in dit project is het transmission_id. Alle boodscha-event entries voor de oorspronkelijke e-mail, gearchiveerde e-mail en alle cc en bcc adressen zullen hetzelfde transmission_id delen.
Er is ook een gemeenschappelijke entry genaamd de message_id die dezelfde id zal hebben voor elke entry van de oorspronkelijke e-mail en de gearchiveerde e-mail. Alle cc of bcc adressen zullen hun eigen id hebben voor de message_id entry.
Tot nu toe klinkt dit geweldig en eerlijk gezegd vrij eenvoudig, maar nu komt het uitdagende deel. Vergeet niet dat om de gearchiveerde e-mail te verkrijgen, we SparkPost moeten laten sturen een duplicaat van de oorspronkelijke e-mail naar een ander e-mailadres dat overeenkomt met een inbox waar je toegang toe hebt. Maar om deze oplossing te automatiseren en de e-mailinhoud op te slaan, ga ik een andere functie van SparkPost gebruiken genaamd Inbound Email Relaying. Wat dat doet, is alle naar een specifiek domein verzonden e-mails nemen en verwerken. Door ze te verwerken, wordt de e-mail uit elkaar gehaald en een JSON-structuur gecreëerd die dan via een webhook naar een applicatie wordt geleverd. Zie Appendix A voor een voorbeeld van een JSON.
Als je heel goed kijkt, zul je merken dat de JSON-structuur van de inkomende relay een zeer belangrijk veld mist; de transmission_id. Terwijl alle uitgaande e-mails dezelfde entry hebben bij de transmission_id, die alle gegevens van de oorspronkelijke e-mail, archive, cc, en bcc adressen bindt; heeft SparkPost geen manier om te weten dat de e-mail vastgelegd door het inkomende proces verbonden is met een van de uitgaande e-mails. Het inkomende proces weet eenvoudigweg dat een e-mail naar een specifiek domein is verzonden en om de e-mail te parseren. Dat is alles. Het zal elke naar dat domein verzonden e-mail op dezelfde manier behandelen, of het nu een antwoord van een klant is of de archief e-mail verzonden vanaf SparkPost.
Dus de truc is; hoe koppel je de uitgaande gegevens aan het inkomende proces dat net de gearchiveerde versie van de e-mail heeft vastgelegd? Wat ik besloot te doen, is een uniek id in de body van de e-mail te verbergen. Hoe dit wordt gedaan, is aan jou, maar ik creëerde eenvoudigweg een invoerveld met het verborgen label aangezet.
Ik heb dat veld ook toegevoegd in het metadata-blok van de X-MSYS-API header die naar SparkPost wordt doorgestuurd tijdens de injectie. Deze verborgen UID zal de lijm zijn voor het hele proces en is een hoofdcomponent van het project en zal in de volgende blogberichten uitgebreid besproken worden.
Nu we de UID hebben die dit project samenbindt en begrijpen waarom het nodig is, kan ik beginnen om de visie van het gehele project en bijbehorende blogposts te bouwen.
Het vastleggen en opslaan van de archive e-mail samen met een database-entry voor zoeken/indexeren
Alle boodschap-gebeurtenisgegevens vastleggen
Een applicatie creëren om de e-mail en alle bijbehorende gegevens te bekijken
Hier is een eenvoudig diagram van het project:

De eerste codeval zal het archiveringsproces en het opslaan van de e-mail op S3 behandelen, terwijl de tweede codeval het opslaan van alle loggegevens van boodschap-gebeurtenissen in MySQL zal behandelen. Je kunt begin 2019 de eerste twee codevallen en blogbijdragen verwachten. Als je vragen of suggesties hebt, aarzel dan niet om ze door te geven.
Fijne verzending.
– Jeff
Bijlage A:
