Cambios en "Plugin: Email Verification and Double Opt-In (DOI) Bundle for Mautic"
Título (English)
- +Plugin: Email Verification and Double Opt-In (DOI) Bundle for Mautic
Cuerpo (English)
-
+
Overview
Double Opt-In, or DOI, is one case of a broader need: a way to prove that a form submission is genuine, that the email address behind it is real and actually belongs to the person who submitted it. That need has only grown more important, and it shows up well beyond marketing consent, in account signups, gated downloads, or any form where a fake or mistyped address should be caught. Mautic has no built-in way to do this. People have had to assemble it manually from campaigns, tokens, and timing workarounds, and no third-party attempt has managed to be both universal and easy to use.
This bundle treats email verification as a native property of the form itself. Actions are split into "immediate" and "after verification," the verification email goes out synchronously on submit, and the confirmation click is tracked independently of Mautic's campaign engine, which removes the race conditions that the campaign-based approach is prone to. Links are HMAC-secured, expiration and follow-up reminders are configurable, and skip conditions let specific contacts bypass verification.
Background and context
The need this plugin addresses isn't new or client-specific: Mautic forum threads asking why there's no built-in double opt-in go back to at least 2017 and have resurfaced repeatedly since, which points to a longstanding, unresolved gap in Mautic core rather than an edge case.
Native Mautic's only path to DOI is a campaign-based pattern, and it has two structural problems. First, speed: the confirmation email only goes out once the campaign's decision job picks up the contact, which is too slow for a process where any delay risks losing the contact's attention. Second, reliability: the confirmation click depends on the contact having fully entered the campaign at the moment they click. If not, Mautic can miss the event, leaving the contact confirmed in reality but stuck "unconfirmed" in the system, and the same race condition affects any post-confirmation action such as segment membership, welcome sequences, or CRM sync.
Earlier third-party plugins addressed pieces of this but never became a general standard, and most fell out of maintenance. That's what led Leuchtfeuer to fund and build this plugin, treating verification as something the form does itself rather than something bolted on via campaigns.
Implementation
The plugin was initially built and released for Mautic 5.2, but got support for Mautic 7 in the meantime as well.
Setting up the DOI all happens in the form itself, under the newly added tab “Email Verification”. Once it is enabled, the user can select their verification email here, redirect URLs and more.
Any Mautic email containing the {doi_link} token can serve as the verification email, so there's no dedicated "DOI email" type, and locale-matched translations are respected. Verification links are HMAC-secured, generated from a hash rather than exposing a predictable submission ID, which protects against tampering and rainbow-table-style lookups.
The Actions tab now distinguishes actions that run immediately on submission from actions that only run after successful verification, both configured on the same form with no campaign required.
Confirmation is recorded in a dedicated table rather than through the campaign engine, so it no longer matters whether the contact has fully entered a campaign when they click.
Follow-up reminder emails (default 24-hour wait) go to contacts who haven't confirmed, links expire after a configurable timeout (default 48 hours), and expired pending submissions can be cleaned up automatically.
Per-form skip conditions let specific contacts bypass verification, for example by country or by browser already being known.
From plugin version 5.2.0, successful and unsuccessful verification attempts appear in the contact's activity timeline. Cron-compatible console commands handle follow-up sending, timeout processing, and cleanup.
Production use also surfaced hardening beyond the initial feature set. Deleting a form used to cascade-delete its DOI submission records via the database foreign key, which was a data-loss risk for compliance records; this was addressed by changing the delete behavior to preserve the record. Also, we are snapshotting the field labels at submission time so historical records stay readable even if the form or its fields change later.
Impact and results
The problem this solves has been documented and requested on Mautic's own forums for close to a decade without a built-in resolution, so this plugin is a direct, funded response to a real, longstanding gap. It's in active production use across multiple Leuchtfeuer client Mautic instances with consent-sensitive email programs.
Very positive feedback was also gained during the German Online Meetup, where multiple participants use the DOI plugin in production for a certain time already.
Lessons learned
A generic feature still needs per-form flexibility: different clients need different skip conditions, follow-up timing, and redirect behavior, which is why configuration lives at the form level rather than as one global setting.
Some of that flexibility couldn't be solved inside this plugin alone. Post-verification actions often need to update a contact field, and Mautic's forms had no built-in way to do that outside of a campaign, and no way to make any form action conditional on a form field or contact field value. Rather than working around that gap locally, Leuchtfeuer contributed an "Update Contact" form action directly into Mautic core (https://github.com/mautic/mautic/pull/15690) and released a separate public plugin that adds the option to make form actions conditional based on form or contact field values (https://github.com/Leuchtfeuer/mautic-conditional-form-actions-bundle). Both are now reusable by any Mautic form, not just DOI-related ones.
Known limitations are documented and regularly updated. Campaign forms still add contacts to the campaign immediately on submission without waiting for verification, and this is called out explicitly in the README so implementers build the necessary check themselves.
Future plans
The roadmap includes a dedicated "Update Marketing Opt-In" form action built on top of the new core Update Contact action, with its own data model for opt-in tracking and support for multiple brand-specific opt-in variants. There's also planned a direct support for Mautic landing pages as feedback or redirect targets, language-aware redirects, multi-brand feedback pages, a per-form follow-up wait time, honeypot/NHI awareness, restricting the DOI email selector to emails that actually contain the {doi_link} token, and a dedicated audit log for verification events on the contact. All future ideas are collected in the README.
Community contributions
The plugin is fully open source, developed openly on GitHub with public issues and pull requests.
Documentation is maintained both in the GitHub README (installation, configuration, cron setup, known issues) and as a public how-to guide on Leuchtfeuer.com aimed at Mautic users without developer support.
Supporting materials
- +
GitHub repository: https://github.com/Leuchtfeuer/mautic-DOI-bundle
- +
Public how-to guide: https://leuchtfeuer.com/mautic/know-how/mautic-doi-plugin/
- +


Compartir