Aller au contenu

Transactionnel

Les e-mails de votre application, enfin gardés

Un reçu qui n’arrive pas, c’est un client qui appelle. Lekalao envoie les e-mails de vos applications par votre fournisseur, et garde chacun au journal.

Essayer gratuitement

Gratuit jusqu’à 1 000 abonnés, sans carte. Formules payantes : 14 jours d’essai.

Trois façons de brancher

L’API
Un POST : des variables, des pièces jointes, la langue, le fournisseur.
Le transport Laravel
MAIL_MAILER=lekalao, et votre code ne change pas.
Le relais SMTP
Pour ce qui ne parle que SMTP : un jeton d’API sert de mot de passe. Le relais lui-même ne parle pas TLS : le service en ligne l’expose en TLS sur le port 465, par le proxy placé devant lui ; une installation auto-hébergée le place derrière le sien.
curl -X POST "$LEKALAO_URL/api/v1/transactional-mails/send" \
  -H "Authorization: Bearer $LEKALAO_TOKEN" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: order-2026-00481-confirmation" \
  -d '{
    "template": "order-confirmation",
    "to": ["ada@example.com"],
    "locale": "fr",
    "variables": {
      "customer": { "name": "Ada" },
      "order": { "number": "2026-00481", "total": "12 500 FCFA" }
    }
  }'
// config/mail.php
'mailers' => [
    'lekalao' => [
        'transport' => 'lekalao-api',
        'endpoint' => env('LEKALAO_URL'),
        'token' => env('LEKALAO_TOKEN'),
    ],
],

// .env: MAIL_MAILER=lekalao
Mail::to($order->customer)->send(new OrderConfirmed($order));
MAIL_MAILER=smtp
MAIL_HOST=$LEKALAO_SMTP_HOST
MAIL_PORT=2525
MAIL_USERNAME=lekalao
# An API token with the "write" ability
MAIL_PASSWORD=$LEKALAO_TOKEN

Le journal répond à « l’a-t-il reçu ? »

Destinataires, contenu, remise, ouvertures, clics, et un bouton pour renvoyer. Des statistiques par modèle.

Deux flux, deux fournisseurs

Les campagnes par l’un, les factures par l’autre. Une campagne qui attire des plaintes n’abîme jamais le flux qui envoie vos reçus.

Des modèles que le marketing peut relire

HTML, Markdown ou MJML, une version par langue, des destinataires par défaut. L’application envoie les variables ; le texte, lui, se corrige sans déploiement.

Des webhooks qui se prouvent

Inscriptions, départs, tags, rebonds, plaintes : chaque appel est signé en HMAC-SHA256. Le journal garde la réponse reçue, et une adresse qui échoue dix fois de suite est désactivée.

Vérifier un webhook

Route::post('/webhooks/lekalao', function (Request $request) {
    $expected = hash_hmac(
        'sha256',
        $request->getContent(),
        config('services.lekalao.webhook_secret'),
    );

    $received = (string) $request->header('X-Lekalao-Signature');

    abort_unless(hash_equals($expected, $received), 401);

    // subscriber.unsubscribed, mail.bounced, campaign.sent…
    return response()->noContent();
});

Tout ce que fait l’interface, votre code le fait aussi

La même clé n’écrit jamais deux fois : une Idempotency-Key rend la première réponse pendant 24 heures. Les limites se comptent par jeton, pas par adresse. Mille abonnés passent en un appel, avec un compte rendu par ligne.

Un test refuse toute route sans description, et toute description sans route.

Pas de SDK, et c’est voulu

Cinq paquets à maintenir pendant que l’API bouge coûteraient plus qu’ils ne rapportent. La spécification OpenAPI est juste ; votre générateur fait le reste. Pour Laravel, le transport est prêt.

Comment c’est fait

Laravel, PostgreSQL, Redis. Plus de 1 000 tests automatisés, dont un qui ouvre chaque page avec des données. Quand les comptes s’ouvrent à la main, le formulaire au pied de ce site est le formulaire d’inscription du produit lui-même.

Commencez gratuitement. Essayez le reste 14 jours.

Gratuit jusqu’à 1 000 abonnés, sans carte. Starter, Growth et Pro s’essaient 14 jours, sans carte non plus ; si vous ne payez pas, votre équipe revient simplement à Gratuit au 15ᵉ jour.