1. Pré-requis
Avant de commencer l'intégration, assurez-vous de disposer des éléments suivants :
| Élément | Description |
|---|---|
| Clé API | Fournie par Securemail via la console d'administration (voir section suivante). |
| Client HTTPS | Tout système capable d'exécuter des requêtes HTTPS GET : curl, Python, Logstash, etc. |
| Outil SIEM | Un outil capable d'ingérer et de traiter du JSON (Splunk, Elastic, Graylog, etc.). |
2. Récupérer votre clé API
La clé API est propre à chaque domaine. Pour la récupérer :
- Connectez-vous à votre console d'administration e-securemail.
- Sélectionnez le domaine concerné.
- Naviguez dans le menu Suivi > Intégration SIEM.
- La clé API est affichée sur cette page.
Astuce : La page d'intégration SIEM affiche également la commande
curlprête à l'emploi avec votre clé pré-remplie, pour tester rapidement la connexion.
Sécurité : Ne partagez jamais votre clé API. Si elle est compromise, régénérez-la depuis la console d'administration.
3. Accès et authentification
Toutes les requêtes doivent être effectuées en HTTPS via la méthode GET. L'authentification repose sur un en-tête Authorization de type Bearer.
En-tête requis :
Authorization: Bearer <CLÉ_API_DOMAINE>Exemple curl :
curl \
--header 'Authorization: Bearer <CLÉ_API>' \
'https://logs.securemail.tech/siem/suivi.php'Sécurité : Conservez la clé API dans une variable d'environnement ou un coffre-fort de secrets. Ne la commitez jamais dans un dépôt de code source ni dans des fichiers de logs.
4. Paramètres de requête
Les trois paramètres ci-dessous définissent la fenêtre temporelle des données retournées. Chaque requête est limitée à une heure de données maximum.
sinceSeconds
Nombre de secondes à remonter dans le passé depuis l'instant de la requête.
/siem/suivi.php?sinceSeconds=3600Données récupérées depuis 1 heure en arrière (3600 secondes).
sinceTime
Date/heure précise à partir de laquelle les données doivent être récupérées. Accepte une date ISO 8601 ou un timestamp Unix.
/siem/suivi.php?sinceTime=2024-06-01T12:00:00Z
/siem/suivi.php?sinceTime=1726869600Données récupérées à partir du 1er juin 2024 à 12h00 UTC.
interval
Intervalle de temps complet (début et fin). Deux dates ou timestamps séparés par un /.
/siem/suivi.php?interval=2024-08-20T15:30:00/2024-08-20T16:00:00
/siem/suivi.php?interval=1727136000/1727139600Données récupérées entre 15h30 et 16h00 le 20 août 2024.
Chaînage sans doublon : La valeur
queryEndTimeretournée dans chaque réponse peut être réutilisée directement comme valeur desinceTimepour la requête suivante, garantissant une collecte continue sans manque ni doublon.
5. Codes de retour HTTP
6. Structure de la réponse JSON
Enveloppe principale
| Champ | Type | Description |
|---|---|---|
queryEndTime |
timestamp Unix | Date de fin de la période couverte. À réutiliser comme sinceTime pour la requête suivante. |
data |
tableau | Liste des messages filtrés. Tableau vide si aucun message sur la période — ce cas est normal et doit être géré dans le collecteur. |
Réponse sans message :
{
"queryEndTime": 1727259183,
"data": []
}7. Référence des champs
Objet message (dans data[])
| Champ | Type | Description |
|---|---|---|
message_id |
texte | Identifiant unique du message. |
client_ip |
adresse IP | Adresse IP du serveur expéditeur. |
client_name |
texte | Nom DNS inverse (PTR) de l'IP expéditrice. |
client_country |
2 lettres | Code pays ISO de l'expéditeur (ex : FR, US). |
helo_name |
texte | Valeur HELO/EHLO présentée par le serveur expéditeur lors de la connexion SMTP. |
stamp_queued |
timestamp Unix | Date et heure de réception du message, avant analyse. |
header_from |
texte | Adresse de l'expéditeur affichée dans l'en-tête From du message (visible par le destinataire). |
sender |
texte | Adresse expéditrice SMTP (enveloppe). Peut différer de header_from (cas fréquent pour les newsletters ou rebonds). |
subject |
texte | Objet du message. |
message_size |
nombre (octets) | Taille totale du message en octets. |
recipients |
tableau | Liste des destinataires. Un objet par destinataire (voir ci-dessous). |
message_parts |
tableau | Liste des parties MIME du message (texte, HTML, pièces jointes). |
Objet destinataire (dans recipients[])
| Champ | Type | Description |
|---|---|---|
recipient |
texte | Adresse email du destinataire. |
stamp_filter |
timestamp Unix | Date à laquelle le filtrage a été effectué pour ce destinataire. |
verdict |
texte | Résultat de l'analyse antispam/antivirus (voir valeurs ci-dessous). |
action |
texte | Action appliquée au message suite au verdict (voir valeurs ci-dessous). |
stamp_delivery |
timestamp Unix | Date de la livraison ou du dernier essai. |
delivery_to_ip |
adresse IP | IP du serveur destinataire ayant reçu (ou tenté de recevoir) le message. |
delivery_to_name |
texte | Nom DNS du serveur destinataire. |
delivery_status |
texte | Statut final de la livraison (voir valeurs ci-dessous). |
delivery_info |
texte | Réponse brute du serveur distant lors de la tentative de livraison (ex : 250 message accepted). |
filter_info |
texte | Détail des règles de filtrage déclenchées et leurs scores individuels. |
antispam_score |
nombre décimal | Score antispam global calculé pour ce message. Plus le score est élevé, plus le message est suspect. |
Valeurs possibles — verdict
| Valeur | Signification |
|---|---|
valid |
Message considéré comme légitime. |
spam |
Message identifié comme spam. |
virus |
Message contenant un virus ou un logiciel malveillant. |
tagged |
Message livré avec une marque (ex : modification du sujet). |
refused |
Message refusé lors de la connexion SMTP, avant analyse complète. |
rejected |
Message rejeté après analyse. |
oversize |
Message dépassant la taille maximale autorisée. |
content |
Message bloqué suite à une règle de filtrage de contenu. |
unchecked |
Message n'ayant pas pu être analysé. |
Valeurs possibles — action
| Valeur | Signification |
|---|---|
pass |
Message livré au destinataire (avec ou sans modification). |
blocked |
Message bloqué, non livré. |
rejected |
Message rejeté au niveau SMTP. |
bounced |
Message renvoyé à l'expéditeur (bounce). |
Valeurs possibles — delivery_status
| Valeur | Signification |
|---|---|
sent |
Message livré avec succès. |
deferred |
Livraison temporairement échouée, sera retentée automatiquement. |
bounced |
Livraison définitivement échouée. |
quarantine |
Message placé en quarantaine. |
rejected |
Message rejeté par le serveur destinataire. |
unknown |
État de livraison indéterminé. |
disconnected |
Connexion interrompue lors de la tentative de livraison. |
Objet partie de message (dans message_parts[])
| Champ | Type | Description |
|---|---|---|
name |
texte | Nom du fichier attaché. Vide pour les parties texte ou HTML inline. |
placement |
nombre | Numéro d'ordre de cette partie dans le message MIME. |
sha1 |
texte | Empreinte SHA-1 du contenu. Utile pour la déduplication ou la détection de fichiers connus. |
size |
nombre (octets) | Taille de la partie en octets. |
content_type |
texte (MIME) | Type MIME (ex : text/plain, text/html, image/png, application/pdf). |
qrcode |
booléen |
true si un QR Code a été détecté dans cette partie — technique couramment utilisée dans les attaques de phishing. |
8. Bonnes pratiques d'intégration
Collecte continue sans perte de données
Pour une collecte sans doublons ni lacune, chaînez les requêtes en réutilisant queryEndTime :
- 1ère requête :
?sinceSeconds=3600→ réponse contientqueryEndTime: 1727259183 - 2ème requête :
?sinceTime=1727259183→ réponse contientqueryEndTime: 1727262783 - 3ème requête :
?sinceTime=1727262783→ et ainsi de suite…
Recommandation : Stockez la dernière valeur
queryEndTimeen base de données ou dans un fichier d'état. En cas de redémarrage du collecteur, reprenez depuis cette valeur pour ne pas perdre de données.
Limite d'une heure par requête
Si vous devez couvrir une période plus longue (après une interruption par exemple), effectuez plusieurs requêtes consécutives en chaînant queryEndTime, jusqu'à rattraper le temps réel.
Gestion du tableau data vide
Un tableau data vide est un cas parfaitement normal indiquant l'absence de message filtré sur la période. Le collecteur doit gérer ce cas sans erreur, mettre à jour la valeur de queryEndTime et poursuivre normalement.
Sécurité de la clé API
Ne stockez jamais la clé API en clair dans le code source. Utilisez une variable d'environnement (SIEM_API_KEY) ou un gestionnaire de secrets. Toutes les requêtes transitent exclusivement en HTTPS.
9. Exemple complet de réponse JSON
json
{
"queryEndTime": 1727259183,
"data": [
{
"message_id": "23e0.64facee0.bc601.0",
"client_ip": "161.38.205.161",
"client_name": "m205-161.eu.mailgun.net",
"client_country": "US",
"helo_name": "m205-161.eu.mailgun.net",
"stamp_queued": 1727254241,
"header_from": "actualites@e.artisanparfumeur.com",
"sender": "bounce+2ba51a.211f8-marie.fini=pur-mail.net@e.artisanparfumeur.com",
"subject": "Signatures intemporelles",
"message_size": 87879,
"recipients": [
{
"recipient": "marie.fini@pur-mail.net",
"stamp_filter": 1727254241,
"verdict": "tagged",
"action": "pass",
"stamp_delivery": 1727254244,
"delivery_to_ip": "172.16.240.194",
"delivery_to_name": "mails.security-mail.net",
"delivery_status": "sent",
"delivery_info": "250 2113927973 message accepted for delivery",
"filter_info": "DKIM_SIGNED=0.1, DKIM_VALID=-0.5, DKIM_VALID_AU=-0.5, DMARC_PASS=-0.5, HEAD_NEWS=-0.5, SPF_PASS=-0.1, S_ENVFROM_LONG_40=0.5, S_FROM_GREY_MINUS_1=-1, T_REMOTE_IMAGE=0.42, URIBL_SECURITYMAIL=10",
"antispam_score": 7.914
}
],
"message_parts": [
{
"name": "",
"placement": 1,
"sha1": "2aa02691eeb412a8ef371a312177bba525c1ee33",
"size": 18528,
"content_type": "text/plain",
"qrcode": false
},
{
"name": "",
"placement": 2,
"sha1": "240171907cc95ab46cd2b4549ebd81dd48ac5d12",
"size": 60556,
"content_type": "text/html",
"qrcode": false
},
{
"name": "image001.png",
"placement": 3,
"sha1": "bb238282b1a443121271a0d4c71c5efbdd8fbb07",
"size": 15473,
"content_type": "image/png",
"qrcode": false
}
]
}
]
}
{
"queryEndTime": 1727259183,
"data": [
{
"message_id": "23e0.64facee0.bc601.0",
"client_ip": "161.38.205.161",
"client_name": "m205-161.eu.mailgun.net",
"client_country": "US",
"helo_name": "m205-161.eu.mailgun.net",
"stamp_queued": 1727254241,
"header_from": "actualites@e.artisanparfumeur.com",
"sender": "bounce+2ba51a.211f8-marie.fini=pur-mail.net@e.artisanparfumeur.com",
"subject": "Signatures intemporelles",
"message_size": 87879,
"recipients": [
{
"recipient": "marie.fini@pur-mail.net",
"stamp_filter": 1727254241,
"verdict": "tagged",
"action": "pass",
"stamp_delivery": 1727254244,
"delivery_to_ip": "172.16.240.194",
"delivery_to_name": "mails.security-mail.net",
"delivery_status": "sent",
"delivery_info": "250 2113927973 message accepted for delivery",
"filter_info": "DKIM_SIGNED=0.1, DKIM_VALID=-0.5, DKIM_VALID_AU=-0.5, DMARC_PASS=-0.5, HEAD_NEWS=-0.5, SPF_PASS=-0.1, S_ENVFROM_LONG_40=0.5, S_FROM_GREY_MINUS_1=-1, T_REMOTE_IMAGE=0.42, URIBL_SECURITYMAIL=10",
"antispam_score": 7.914
}
],
"message_parts": [
{
"name": "",
"placement": 1,
"sha1": "2aa02691eeb412a8ef371a312177bba525c1ee33",
"size": 18528,
"content_type": "text/plain",
"qrcode": false
},
{
"name": "",
"placement": 2,
"sha1": "240171907cc95ab46cd2b4549ebd81dd48ac5d12",
"size": 60556,
"content_type": "text/html",
"qrcode": false
},
{
"name": "image001.png",
"placement": 3,
"sha1": "bb238282b1a443121271a0d4c71c5efbdd8fbb07",
"size": 15473,
"content_type": "image/png",
"qrcode": false
}
]
}
]
}