{"id":278290,"date":"2026-01-29T23:55:58","date_gmt":"2026-01-29T23:55:58","guid":{"rendered":"https:\/\/wordpress.org\/plugins\/smtp-postal\/"},"modified":"2026-03-31T07:19:04","modified_gmt":"2026-03-31T07:19:04","slug":"oderland-smtp-postal-mailer","status":"publish","type":"plugin","link":"https:\/\/twd.wordpress.org\/plugins\/oderland-smtp-postal-mailer\/","author":20751464,"comment_status":"closed","ping_status":"closed","template":"","meta":{"_crdt_document":"","version":"1.4.1","stable_tag":"1.4.1","tested":"6.9.4","requires":"5.7","requires_php":"8.1","requires_plugins":null,"header_name":"Oderland SMTP & Postal Mailer","header_author":"Oderland Webbhotell AB","header_description":"Send emails via SMTP or Postal API with multiple account support, priority-based failover, comprehensive logging, and delivery tracking via webhooks.","assets_banners_color":"fafafa","last_updated":"2026-03-31 07:19:04","external_support_url":"","external_repository_url":"","donate_link":"","header_plugin_uri":"","header_author_uri":"https:\/\/www.oderland.com","rating":5,"author_block_rating":0,"active_installs":30,"downloads":680,"num_ratings":1,"support_threads":0,"support_threads_resolved":0,"author_block_count":0,"sections":["description","installation","faq","changelog"],"tags":{"1.1.0":{"tag":"1.1.0","author":"oderlandab","date":"2026-01-29 23:56:19"},"1.1.1":{"tag":"1.1.1","author":"oderlandab","date":"2026-01-30 09:02:40"},"1.1.2":{"tag":"1.1.2","author":"oderlandab","date":"2026-02-07 12:24:13"},"1.2.0":{"tag":"1.2.0","author":"oderlandab","date":"2026-02-09 22:46:20"},"1.3.0":{"tag":"1.3.0","author":"oderlandab","date":"2026-02-14 19:03:15"},"1.3.1":{"tag":"1.3.1","author":"oderlandab","date":"2026-03-06 13:21:56"},"1.3.2":{"tag":"1.3.2","author":"oderlandab","date":"2026-03-11 16:53:10"},"1.3.3":{"tag":"1.3.3","author":"oderlandab","date":"2026-03-18 08:57:49"},"1.4.0":{"tag":"1.4.0","author":"oderlandab","date":"2026-03-20 11:50:28"},"1.4.1":{"tag":"1.4.1","author":"oderlandab","date":"2026-03-31 07:19:04"}},"upgrade_notice":{"1.3.1":"<p>Security hardening release. SMTP passwords are now encrypted and the encryption key is derived from wp-config.php constants. Existing credentials are migrated automatically. Note: if you later change AUTH_KEY or SECURE_AUTH_KEY in wp-config.php, you will need to re-enter your account credentials.<\/p>","1.0.0":"<p>First stable release with security improvements and WordPress 6.9 compatibility.<\/p>","0.1.4":"<p>Simplified account setup with consolidated from address field.<\/p>","0.1.3":"<p>Improved reliability with better failover handling and SMTP debugging capabilities.<\/p>"},"ratings":{"1":0,"2":0,"3":0,"4":0,"5":1},"assets_icons":{"icon-128x128.png":{"filename":"icon-128x128.png","revision":3455917,"resolution":"128x128","location":"assets","locale":""},"icon-256x256.png":{"filename":"icon-256x256.png","revision":3455917,"resolution":"256x256","location":"assets","locale":""}},"assets_banners":{"banner-1544x500-sv_SE.png":{"filename":"banner-1544x500-sv_SE.png","revision":3455917,"resolution":"1544x500","location":"assets","locale":"sv_SE"},"banner-1544x500.png":{"filename":"banner-1544x500.png","revision":3455917,"resolution":"1544x500","location":"assets","locale":""},"banner-772x250-sv_SE.png":{"filename":"banner-772x250-sv_SE.png","revision":3455917,"resolution":"772x250","location":"assets","locale":"sv_SE"},"banner-772x250.png":{"filename":"banner-772x250.png","revision":3455917,"resolution":"772x250","location":"assets","locale":""}},"assets_blueprints":{},"all_blocks":[],"tagged_versions":["1.1.0","1.1.1","1.1.2","1.2.0","1.3.0","1.3.1","1.3.2","1.3.3","1.4.0","1.4.1"],"block_files":[],"assets_screenshots":{"screenshot-1.png":{"filename":"screenshot-1.png","revision":3450070,"resolution":"1","location":"assets","locale":""},"screenshot-2.png":{"filename":"screenshot-2.png","revision":3450070,"resolution":"2","location":"assets","locale":""},"screenshot-3.png":{"filename":"screenshot-3.png","revision":3450070,"resolution":"3","location":"assets","locale":""},"screenshot-4.png":{"filename":"screenshot-4.png","revision":3450070,"resolution":"4","location":"assets","locale":""},"screenshot-5.png":{"filename":"screenshot-5.png","revision":3450070,"resolution":"5","location":"assets","locale":""},"screenshot-6.png":{"filename":"screenshot-6.png","revision":3450070,"resolution":"6","location":"assets","locale":""},"screenshot-7.png":{"filename":"screenshot-7.png","revision":3457532,"resolution":"7","location":"assets","locale":""}},"screenshots":{"1":"Accounts management - Configure multiple mail accounts with priority","2":"Email logs - View sent emails with delivery status","3":"Log details - Inspect individual email details and events","4":"Settings - Configure logging and failover behavior","5":"Test email - Send test emails to verify configuration","6":"Postal settings - Setting up a Postal account","7":"Dashboard - Email statistics with volume chart, account breakdown, and failure analysis"},"jetpack_post_was_ever_published":false},"plugin_section":[],"plugin_tags":[17561,267,450,43476,6696],"plugin_category":[41],"plugin_contributors":[254917],"plugin_business_model":[],"class_list":["post-278290","plugin","type-plugin","status-publish","hentry","plugin_tags-deliverability","plugin_tags-email","plugin_tags-mail","plugin_tags-postal","plugin_tags-smtp","plugin_category-communication","plugin_contributors-oderlandab","plugin_committers-oderlandab"],"banners":{"banner":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/banner-772x250.png?rev=3455917","banner_2x":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/banner-1544x500.png?rev=3455917","banner_rtl":false,"banner_2x_rtl":false},"icons":{"svg":false,"icon":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/icon-128x128.png?rev=3455917","icon_2x":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/icon-256x256.png?rev=3455917","generated":false},"screenshots":[{"src":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/screenshot-1.png?rev=3450070","caption":"Accounts management - Configure multiple mail accounts with priority"},{"src":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/screenshot-2.png?rev=3450070","caption":"Email logs - View sent emails with delivery status"},{"src":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/screenshot-3.png?rev=3450070","caption":"Log details - Inspect individual email details and events"},{"src":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/screenshot-4.png?rev=3450070","caption":"Settings - Configure logging and failover behavior"},{"src":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/screenshot-5.png?rev=3450070","caption":"Test email - Send test emails to verify configuration"},{"src":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/screenshot-6.png?rev=3450070","caption":"Postal settings - Setting up a Postal account"},{"src":"https:\/\/ps.w.org\/oderland-smtp-postal-mailer\/assets\/screenshot-7.png?rev=3457532","caption":"Dashboard - Email statistics with volume chart, account breakdown, and failure analysis"}],"raw_content":"<!--section=description-->\n<p>Oderland SMTP &amp; Postal Mailer is a plugin that allows you to send transactional emails using <a href=\"https:\/\/en.wikipedia.org\/wiki\/Simple_Mail_Transfer_Protocol\">SMTP<\/a> or <a href=\"https:\/\/docs.postalserver.io\/\">Postal<\/a> API. Easy-to-use for e-mail logging and making sure your e-mails make it all the way to your intended target.<\/p>\n\n<p>The plugin works with any SMTP mailer you're using, including but not limited to <a href=\"https:\/\/www.oderland.se\/postal\">Oderland Postal<\/a>.<\/p>\n\n<p><strong>What is SMTP and why do you need it?<\/strong><\/p>\n\n<p>SMTP (Simple Mail Transfer Protocol) is the standard that ensures that emails actually arrive at their destination. It's a protocol that delivers your email between servers when you click \"send\" in your email client.<\/p>\n\n<p>You could say that with an SMTP plugin or service, you want to confirm to the email servers that what you're sending isn't spam, which lends authenticity to your mailings.<\/p>\n\n<p><strong>Features:<\/strong><\/p>\n\n<ul>\n<li>Send transactional emails via SMTP, Postal API or PHP mail()<\/li>\n<li>Multiple mail account support with priority-based failover<\/li>\n<li>Automatic retry on temporary failures with exponential backoff<\/li>\n<li>Comprehensive email logging with configurable retention<\/li>\n<li>Statistics dashboard \u2014 email volume over time, delivery success rates, per-account breakdown, failure analysis, recipient domain insights, and send time patterns<\/li>\n<li>CSV export of all dashboard statistics<\/li>\n<li>WordPress admin dashboard widget with 7-day email summary<\/li>\n<li>Engagement tracking (opens, clicks) for Postal accounts<\/li>\n<li>Postal webhook integration for delivery status tracking<\/li>\n<li>Per-account webhook debug logging for Postal accounts<\/li>\n<li>Secure credential storage with AES-256 encryption<\/li>\n<li>Protocol-level SMTP debugging<\/li>\n<\/ul>\n\n<p><strong>Services Supported:<\/strong><\/p>\n\n<ul>\n<li><strong>SMTP<\/strong> \u2013 Connect to any SMTP server<\/li>\n<li><strong><a href=\"https:\/\/docs.postalserver.io\/\">Postal<\/a><\/strong> \u2013 Integration with Postal mail delivery platform<\/li>\n<li><strong>Local<\/strong> \u2013 Fallback to PHP mail() function<\/li>\n<\/ul>\n\n<!--section=installation-->\n<ol>\n<li>Upload the <code>oderland-smtp-postal-mailer<\/code> folder to the <code>\/wp-content\/plugins\/<\/code> directory<\/li>\n<li>Activate the plugin through the 'Plugins' menu in WordPress<\/li>\n<li>Go to Settings &gt; Oderland SMTP &amp; Postal Mailer to configure your mail accounts<\/li>\n<li>Add at least one mail account (SMTP or Postal)<\/li>\n<li>Send a test email to verify your configuration<\/li>\n<\/ol>\n\n<!--section=faq-->\n<dl>\n<dt id=\"how%20do%20i%20configure%20smtp%3F\"><h3>How do I configure SMTP?<\/h3><\/dt>\n<dd><p>Go to Settings &gt; Oderland SMTP &amp; Postal Mailer &gt; Accounts and click \"Add Account\". Select SMTP as the service type and enter your SMTP server details including host, port, username, and password.<\/p><\/dd>\n<dt id=\"how%20does%20the%20failover%20work%3F\"><h3>How does the failover work?<\/h3><\/dt>\n<dd><p>Accounts are tried in priority order (lower number = higher priority). If sending fails with a temporary error, the plugin retries with exponential backoff. If all retries fail, it moves to the next account.<\/p><\/dd>\n<dt id=\"what%20gets%20logged%3F\"><h3>What gets logged?<\/h3><\/dt>\n<dd><p>By default, the plugin logs email headers, recipients, and subjects. You can optionally enable body logging. Logs are automatically removed after 30 days (configurable).<\/p><\/dd>\n<dt id=\"how%20do%20i%20set%20up%20postal%20webhooks%3F\"><h3>How do I set up Postal webhooks?<\/h3><\/dt>\n<dd><p>When you create a Postal account, the plugin generates a webhook URL. Add this URL in your Postal server's webhook settings to receive delivery status updates.<\/p><\/dd>\n<dt id=\"is%20my%20smtp%20password%20secure%3F\"><h3>Is my SMTP password secure?<\/h3><\/dt>\n<dd><p>Yes. All sensitive credentials (SMTP passwords, API keys) are encrypted using AES-256-GCM. The encryption key is derived from your WordPress auth constants in wp-config.php, so it is never stored in the database.<\/p><\/dd>\n\n<\/dl>\n\n<!--section=changelog-->\n<h4>1.4.1<\/h4>\n\n<ul>\n<li>Fixed fatal TypeError in automatic log cleanup when deleting old mail entries<\/li>\n<\/ul>\n\n<h4>1.4.0<\/h4>\n\n<ul>\n<li>Added bounce export feature: download bounced\/failed email addresses as CSV or JSON from the Logs page<\/li>\n<li>Show delivery failures (MessageDeliveryFailed) in Account Breakdown, Service Comparison, Domain Insights tables, charts, and CSV export on the Dashboard<\/li>\n<li>Added explanatory note on Dashboard distinguishing Sent\/Failed from Bounced\/Delivery Failed<\/li>\n<li>Fixed Domain Insights not showing bounced\/delivery failed counts for Postal webhook events<\/li>\n<li>Fixed sorting by Service or Status columns on the Logs page causing a database error<\/li>\n<li>Added sorting by Recipient column on the Logs page<\/li>\n<li>Code quality: resolved all PHPStan level 8 errors and all PHPCS coding standard violations<\/li>\n<\/ul>\n\n<h4>1.3.3<\/h4>\n\n<ul>\n<li>Fixed emails with Swedish characters (\u00e5 \u00e4 \u00f6) showing scrambled MIME headers instead of rendered HTML<\/li>\n<li>Filter out Content-Type, Content-Transfer-Encoding, and MIME-Version headers that conflict with transport layer<\/li>\n<li>Respect Content-Type: text\/plain header to force plain text emails<\/li>\n<li>Fixed bulk delete action label mismatch in log table<\/li>\n<\/ul>\n\n<h4>1.3.2<\/h4>\n\n<ul>\n<li>Fixed SMTP mailer not honoring Reply-To headers passed by wp_mail() (e.g. from form plugins)<\/li>\n<li>Fixed SMTP mailer not forwarding custom headers (X-Mailer, X-Priority, etc.)<\/li>\n<li>Fixed CC and BCC headers from wp_mail() not being handled as proper recipients<\/li>\n<li>Fixed From header from wp_mail() not being parsed into structured sender field<\/li>\n<li>SMTP Reply-To now uses same priority as Postal: wp_mail header first, account config fallback<\/li>\n<li>wp_mail() headers (CC, BCC, Reply-To, From) are now parsed like WordPress core does<\/li>\n<\/ul>\n\n<h4>1.3.1<\/h4>\n\n<ul>\n<li>Security: SMTP credentials (password) are now encrypted at rest using AES-256-GCM<\/li>\n<li>Security: Encryption key is now derived from WordPress auth constants (AUTH_KEY\/SECURE_AUTH_KEY) instead of being stored in the database<\/li>\n<li>Security: Added input sanitization for SMTP service data fields (hostname, port, username, secure protocol)<\/li>\n<li>Security: Added SQL alias allowlist validation in statistics queries<\/li>\n<li>Security: Added direct file access guards to remaining PHP files<\/li>\n<li>Existing credentials are automatically re-encrypted during upgrade<\/li>\n<\/ul>\n\n<h4>1.3.0<\/h4>\n\n<ul>\n<li>Added DNS warning system for Postal accounts \u2014 automatically displays warnings when Postal detects DNS issues (SPF, DKIM, MX, Return Path) for your sending domain<\/li>\n<li>Added DNS warnings to the edit-account page, accounts list, and WordPress dashboard widget with dismiss buttons<\/li>\n<li>Added \"DNS warnings\" setting under Settings &gt; Postal Webhooks (enabled by default)<\/li>\n<li>Added per-account webhook debug logging for Postal accounts \u2014 toggle on the edit-account page to log the last 10 incoming webhooks (successful, failed auth, errors, and filtered DNS events)<\/li>\n<li>Added \"Clear debug log\" button to reset entries per account<\/li>\n<li>Added cleanup of webhook debug log and DNS error data on plugin uninstall<\/li>\n<li>Fixed \"From address\" required indicator missing on initial page load<\/li>\n<li>Fixed accordion payload row spacing in log details and webhook debug<\/li>\n<li>Fixed settings page \"Log timing metrics\" description alignment<\/li>\n<li>Removed deprecated load_plugin_textdomain() call<\/li>\n<\/ul>\n\n<h4>1.2.0<\/h4>\n\n<ul>\n<li>Added statistics dashboard with summary cards, time-series chart, and account breakdown<\/li>\n<li>Added delivery insights with failure analysis, failover monitoring, and service comparison<\/li>\n<li>Added recipient domain insights and top recipients table<\/li>\n<li>Added engagement tracking (open rate, click rate) for Postal accounts<\/li>\n<li>Added send time pattern charts (hour of day, day of week)<\/li>\n<li>Added CSV export for all dashboard statistics<\/li>\n<li>Added WordPress admin dashboard widget with 7-day email summary<\/li>\n<li>Added REST API endpoint for aggregated statistics with transient caching<\/li>\n<li>Fixed test email template not showing red header background in Outlook<\/li>\n<li>Improved Swedish translations throughout dashboard<\/li>\n<li>Security: Improved input validation for database queries<\/li>\n<li>Security: Added output escaping throughout admin tables<\/li>\n<li>Security: Hardened email header processing<\/li>\n<li>Security: Added authentication to REST endpoints<\/li>\n<li>Security: Upgraded encryption to AES-256-GCM with backward compatibility<\/li>\n<li>Security: Moved sensitive storage to wp_options<\/li>\n<\/ul>\n\n<h4>1.1.2<\/h4>\n\n<ul>\n<li>Updated brand colors to match Oderland guidelines<\/li>\n<li>Made Oderland logo in header clickable, linking to oderland.se\/postal<\/li>\n<li>Fixed SQL injection vulnerability and wpdb::prepare errors in account search<\/li>\n<li>Implemented log search functionality (search by subject, account, service, recipient)<\/li>\n<li>Fixed plugin action links (Settings, Accounts, Logs) not showing on plugins page<\/li>\n<li>Made account and log table rows clickable to navigate to edit\/details page<\/li>\n<li>Styled input placeholders to be visibly greyed out<\/li>\n<li>Fixed Swedish translations and made Save Settings translatable<\/li>\n<li>Changed enable\/disable icons to play\/pause in account table<\/li>\n<li>Fixed Postal account form: mark webhook key as required and hide non-selected service form<\/li>\n<li>Fixed JavaScript text domain mismatch preventing datetime translations<\/li>\n<li>Regenerated .pot file to include JavaScript translatable strings<\/li>\n<\/ul>\n\n<h4>1.1.1<\/h4>\n\n<ul>\n<li>Fixed missing vendor directory in distribution causing plugin activation failure<\/li>\n<\/ul>\n\n<h4>1.1.0<\/h4>\n\n<ul>\n<li>Renamed plugin to \"Oderland SMTP &amp; Postal Mailer\" for WordPress.org submission<\/li>\n<li>Added migration for existing users from old plugin name<\/li>\n<li>Fixed input sanitization issues<\/li>\n<li>Moved inline scripts to external JavaScript file<\/li>\n<li>Moved inline styles to CSS file<\/li>\n<\/ul>\n\n<h4>1.0.0<\/h4>\n\n<ul>\n<li>First stable release<\/li>\n<li>Added direct file access protection to all PHP files<\/li>\n<li>Added settings sanitization for improved security<\/li>\n<li>Removed deprecated load_plugin_textdomain call<\/li>\n<li>Updated WordPress compatibility to 6.9<\/li>\n<\/ul>\n\n<h4>0.1.4<\/h4>\n\n<ul>\n<li>Consolidated from address fields - removed duplicate address field from Postal service form<\/li>\n<li>From address now required and validated for SMTP and Postal services<\/li>\n<li>Added client-side and server-side validation for from address<\/li>\n<\/ul>\n\n<h4>0.1.3<\/h4>\n\n<ul>\n<li>Added protocol-level SMTP logging with timing metrics<\/li>\n<li>Implemented improved failover logic with retry support<\/li>\n<li>Lowered WordPress requirement from 6.3 to 5.7<\/li>\n<\/ul>\n\n<h4>0.1.2<\/h4>\n\n<ul>\n<li>Major overhaul of the plugin<\/li>\n<\/ul>\n\n<h4>0.1.0<\/h4>\n\n<ul>\n<li>Initial release<\/li>\n<\/ul>","raw_excerpt":"Send transactional emails from WordPress using SMTP or Postal with logging and delivery tracking.","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/plugin\/278290","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/plugin"}],"about":[{"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/types\/plugin"}],"replies":[{"embeddable":true,"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/comments?post=278290"}],"author":[{"embeddable":true,"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wporg\/v1\/users\/oderlandab"}],"wp:attachment":[{"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/media?parent=278290"}],"wp:term":[{"taxonomy":"plugin_section","embeddable":true,"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/plugin_section?post=278290"},{"taxonomy":"plugin_tags","embeddable":true,"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/plugin_tags?post=278290"},{"taxonomy":"plugin_category","embeddable":true,"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/plugin_category?post=278290"},{"taxonomy":"plugin_contributors","embeddable":true,"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/plugin_contributors?post=278290"},{"taxonomy":"plugin_business_model","embeddable":true,"href":"https:\/\/twd.wordpress.org\/plugins\/wp-json\/wp\/v2\/plugin_business_model?post=278290"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}