<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom">
  <id>https://lettr.com/changelog/</id>
  <title>Lettr Changelog</title>
  <subtitle>Everything we ship to Lettr, month by month: new features, improvements and bugfixes across the transactional email API, campaigns, audience and the platform.</subtitle>
  <link rel="alternate" type="text/html" href="https://lettr.com/changelog/"/>
  <link rel="self" type="application/atom+xml" href="https://lettr.com/changelog/feed.xml"/>
  <updated>2026-09-30T00:00:00Z</updated>
  <author><name>Lettr</name><uri>https://lettr.com</uri></author>
  <entry>
    <id>https://lettr.com/changelog/2026-09/</id>
    <title>Lettr changelog: September 2026</title>
    <link rel="alternate" type="text/html" href="https://lettr.com/changelog/2026-09/"/>
    <published>2026-09-30T00:00:00Z</published>
    <updated>2026-09-30T00:00:00Z</updated>
    <summary>Everything Lettr shipped in September 2026: 2 new features, 12 improvements and 20 bugfixes, including Multilingual Campaigns and WebAuthn Passkey Sign-In.</summary>
    <content type="html">&lt;h2&gt;New features&lt;/h2&gt;&lt;h3&gt;Multilingual Campaigns&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Campaigns can now send each recipient the email in their own language, with its own subject line and sender.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Each contact's language comes from a contact property you choose, in Audience → Properties or through the API with &lt;code class=&quot;changelog-code&quot;&gt;purpose: communication_language&lt;/code&gt;. A value like &lt;code class=&quot;changelog-code&quot;&gt;de-AT&lt;/code&gt; gets the German version when there is no Austrian one, and contacts with no language, or one the email doesn't have, get the email's main language. Every language has its own subject, sender and reply-to address, its own unsubscribe footer and its own web version. A language can send from any of your verified sending domains, or change only the domain and keep the part before the @.&lt;/p&gt;&lt;p&gt;Before sending, Review &amp;amp; Send lists each language with its number of recipients and the subject, sender and reply-to it will use. It warns when no contact property holds a language. Test sends let you pick the language, and multilingual emails are marked in the email lists and the campaign picker (&lt;code class=&quot;changelog-code&quot;&gt;EN · SK +2&lt;/code&gt;).&lt;/p&gt;&lt;p&gt;The email is locked when the campaign is scheduled, so later edits don't change what is sent. After sending, campaign activity shows which language each recipient received.&lt;/p&gt;&lt;p&gt;A new preview on the campaign page shows the email in any of its languages, or exactly as a chosen contact will see it, with their details filled in. It works for every campaign, not only multilingual ones, and replaces the old HTML preview.&lt;/p&gt;&lt;h3&gt;WebAuthn Passkey Sign-In&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Signing in to Lettr now works with a passkey (Touch ID, Windows Hello, a phone or a security key) instead of a password.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Add, rename and remove passkeys in Settings → Two-Factor Auth. The login page has a “Sign in with passkey” button, and a passkey counts as both sign-in steps, so there is no second one. Passkeys also work on the “Confirm your identity” prompt and when accepting a team invitation, and accounts that also use an authenticator app get a “Use a passkey instead” option on the two-factor screen.&lt;/p&gt;&lt;p&gt;A passkey does not turn on two-factor authentication, and it does not meet a team's “require 2FA” rule. That rule still needs an authenticator app.&lt;/p&gt;&lt;h2&gt;Improvements&lt;/h2&gt;&lt;h3&gt;Scheduled Emails Are Queued In Lettr Until Send Time&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Scheduled emails now stay in Lettr until their send time, which makes cancelling them work again.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Cancelling with &lt;code class=&quot;changelog-code&quot;&gt;DELETE /emails/scheduled/{id}&lt;/code&gt; had stopped working for every scheduled email. It now works up to the moment of sending, and a scheduled email always shows its current status: &lt;code class=&quot;changelog-code&quot;&gt;scheduled&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;sending&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;sent&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;cancelled&lt;/code&gt; or &lt;code class=&quot;changelog-code&quot;&gt;failed&lt;/code&gt;.&lt;/p&gt;&lt;p&gt;The new &lt;code class=&quot;changelog-code&quot;&gt;GET /emails/scheduled&lt;/code&gt; lists your scheduled emails, and emails can now be scheduled up to 30 days ahead instead of 3. Custom headers, which scheduled emails used to leave out, are now included, and a scheduled email counts against your quota on the day it is sent.&lt;/p&gt;&lt;p&gt;Scheduling now returns a Lettr id that starts with &lt;code class=&quot;changelog-code&quot;&gt;sch_&lt;/code&gt;. The &lt;code class=&quot;changelog-code&quot;&gt;transmission_id&lt;/code&gt; field stays &lt;code class=&quot;changelog-code&quot;&gt;null&lt;/code&gt; until the email is sent, so update any code that reads it from the scheduling response. Old ids still work with &lt;code class=&quot;changelog-code&quot;&gt;GET&lt;/code&gt;.&lt;/p&gt;&lt;h3&gt;Stricter Validation Across Domain, Email, Webhook And Audience Endpoints&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Several API endpoints now reject requests they used to accept, so check these changes against your integration.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Adding a sending domain your team already has returns a 409 error instead of replacing it and resetting its verification. &lt;code class=&quot;changelog-code&quot;&gt;GET /emails&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;GET /emails/events&lt;/code&gt; only search the roughly 10 days of events that are kept: an earlier &lt;code class=&quot;changelog-code&quot;&gt;from&lt;/code&gt; is moved forward, the response shows the dates actually searched, and a &lt;code class=&quot;changelog-code&quot;&gt;to&lt;/code&gt; before &lt;code class=&quot;changelog-code&quot;&gt;from&lt;/code&gt; is rejected. &lt;code class=&quot;changelog-code&quot;&gt;next_cursor&lt;/code&gt; should now be passed back exactly as received; old cursors still work, and an invalid one returns 422.&lt;/p&gt;&lt;p&gt;Webhook names can be at most 24 characters, and a webhook update must change something and send credentials together with &lt;code class=&quot;changelog-code&quot;&gt;auth_type&lt;/code&gt;. Contacts can only be added to lists that belong to your team, a topic's &lt;code class=&quot;changelog-code&quot;&gt;contacts_count&lt;/code&gt; counts only subscribed contacts, and &lt;code class=&quot;changelog-code&quot;&gt;POST /campaigns/{id}/unschedule&lt;/code&gt; can now clear a send time saved on a draft.&lt;/p&gt;&lt;h3&gt;Remote MCP Server Expanded From 18 To 77 Tools&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The remote MCP server at &lt;code class=&quot;changelog-code&quot;&gt;app.lettr.com/mcp&lt;/code&gt; now has all 77 tools of the &lt;code class=&quot;changelog-code&quot;&gt;lettr-mcp&lt;/code&gt; npm package, up from 18.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;An AI assistant connected by signing in can now manage emails and folders, schedule and cancel sends, set up sending domains and webhooks, run campaigns and manage your whole audience. Each tool does exactly what the matching API endpoint does. Tools that change data follow team roles and are marked as destructive, so the assistant can ask you before using them.&lt;/p&gt;&lt;p&gt;Desktop apps such as Claude Code and Cursor can now sign in to the remote server; their sign-in used to be rejected. The same work closed a gap where the sign-in check accepted addresses that only look local, such as &lt;code class=&quot;changelog-code&quot;&gt;http://localhost:1@evil.com&lt;/code&gt;.&lt;/p&gt;&lt;h3&gt;Idempotency-Key Header For The Send Email Endpoint&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;&lt;code class=&quot;changelog-code&quot;&gt;POST /emails&lt;/code&gt; now accepts an &lt;code class=&quot;changelog-code&quot;&gt;Idempotency-Key&lt;/code&gt; header, so a retried request does not send the same email twice.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A repeated request with the same key returns the original response with &lt;code class=&quot;changelog-code&quot;&gt;Idempotency-Replayed: true&lt;/code&gt;, and the email is not sent or counted against your quota again. Keys last 24 hours, belong to one API key, and can be up to 255 letters, digits, &lt;code class=&quot;changelog-code&quot;&gt;.&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;_&lt;/code&gt; or &lt;code class=&quot;changelog-code&quot;&gt;-&lt;/code&gt;.&lt;/p&gt;&lt;p&gt;Reusing a key with a different request returns 409 &lt;code class=&quot;changelog-code&quot;&gt;idempotency_key_conflict&lt;/code&gt;, and retrying while the first request is still running returns 409 &lt;code class=&quot;changelog-code&quot;&gt;idempotency_in_progress&lt;/code&gt; with &lt;code class=&quot;changelog-code&quot;&gt;Retry-After: 1&lt;/code&gt;. The usual checks still run first, so a retry with no quota left still gets a 429. Scheduled sends (&lt;code class=&quot;changelog-code&quot;&gt;POST /emails/scheduled&lt;/code&gt;) ignore the header.&lt;/p&gt;&lt;h3&gt;Templates API Supports Campaign Imports, Folder Listing And Render Status&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The Templates API can now import emails into the marketing module, list folders, and report when an email is ready to send.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Set the new &lt;code class=&quot;changelog-code&quot;&gt;purpose&lt;/code&gt; field to &lt;code class=&quot;changelog-code&quot;&gt;campaign&lt;/code&gt; on &lt;code class=&quot;changelog-code&quot;&gt;POST /templates&lt;/code&gt; to import an email straight into the marketing module and the campaign picker. Without a &lt;code class=&quot;changelog-code&quot;&gt;folder_id&lt;/code&gt; it goes to that module's main folder, and a folder from the other module is rejected with a 422. The new &lt;code class=&quot;changelog-code&quot;&gt;GET /folders&lt;/code&gt; lists your folders with their ids, and &lt;code class=&quot;changelog-code&quot;&gt;GET /templates&lt;/code&gt; can filter by &lt;code class=&quot;changelog-code&quot;&gt;purpose&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;folder_id&lt;/code&gt;. &lt;code class=&quot;changelog-code&quot;&gt;purpose&lt;/code&gt; can't be changed later with &lt;code class=&quot;changelog-code&quot;&gt;PUT /templates/{slug}&lt;/code&gt;.&lt;/p&gt;&lt;p&gt;Imports are now checked: JSON that is not a Topol editor design is rejected with a 422, where it used to be saved as an email that broke when opened. The HTML is now created in the background, so large imports no longer time out and thumbnails no longer stay blank.&lt;/p&gt;&lt;p&gt;Every email now has a &lt;code class=&quot;changelog-code&quot;&gt;preparation_status&lt;/code&gt; (&lt;code class=&quot;changelog-code&quot;&gt;pending&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;ready&lt;/code&gt; or &lt;code class=&quot;changelog-code&quot;&gt;failed&lt;/code&gt;), so you can check that an imported or updated email is ready before sending it.&lt;/p&gt;&lt;h3&gt;Inbound Domains Require A Verified Forwarding URL&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Creating an inbound domain now requires a forwarding URL, which Lettr tests before the domain is created.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Inbound domains used to be created with nowhere to forward mail to, so incoming mail was accepted and then lost while the domain still looked fine. The forwarding URL, with an optional auth token, is now tested when the domain is created. When the endpoint rejects the test, for example because of a firewall, its response is shown and the domain is not created.&lt;/p&gt;&lt;p&gt;Existing inbound domains show a Mail Forwarding card for adding the missing URL. Domain pages now show one clear status, either “receiving mail” or what is missing, and a failed MX check shows where mail is actually going.&lt;/p&gt;&lt;h3&gt;Dedicated Rate Limits For Sandbox API Keys&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Sandbox API keys now allow 20 requests per second, 120 per minute and 2,000 per day, up from 10 per minute and 100 per day.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;They no longer share the team's limit of 3 requests per second, so CLI commands like &lt;code class=&quot;changelog-code&quot;&gt;lettr:init&lt;/code&gt; and DTO generation no longer stall. New &lt;code class=&quot;changelog-code&quot;&gt;X-Sandbox-RateLimit-Second-*&lt;/code&gt; headers show the sandbox limits, and the standard &lt;code class=&quot;changelog-code&quot;&gt;X-RateLimit-*&lt;/code&gt; headers keep working with existing SDKs.&lt;/p&gt;&lt;h3&gt;Per-Message Open And Click Tracking Headers For SMTP&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Open and click tracking can now be turned off for a single SMTP message with &lt;code class=&quot;changelog-code&quot;&gt;X-Lettr-Track-Opens: false&lt;/code&gt; or &lt;code class=&quot;changelog-code&quot;&gt;X-Lettr-Track-Clicks: false&lt;/code&gt;.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The headers are removed before the email is delivered. An invalid value rejects the message with &lt;code class=&quot;changelog-code&quot;&gt;554 5.6.0&lt;/code&gt; instead of sending it with tracking on.&lt;/p&gt;&lt;h3&gt;Event Type Filter And Readable Out-Of-Band Reports On The Events Page&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The Events page has a new event type filter (Injected, Delivered, Bounce and others) that stays set as you page through results or switch to sandbox mode.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Reports that arrive separately from the original email, and can't be matched to it, used to show as rows of empty fields. They now explain what happened, with the reason and optional technical details. Automatic and out-of-office replies are labelled “Auto-reply”, with a note that the email did not fail.&lt;/p&gt;&lt;h3&gt;Contact Properties In The Marketing Editor's Merge-Tag Menu&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The merge-tag menu in the marketing email editor has a new Audience group with the recipient's email and all of your team's contact properties.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The unsubscribe and web version links are now always available in the menu too.&lt;/p&gt;&lt;h3&gt;Empty-Value Conditions For Segment Properties&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Segments can now match properties that are empty or not empty, for text, number, true/false, date and JSON properties, in the app and through the API.&lt;/strong&gt;&lt;/p&gt;&lt;h3&gt;Emails List Preserves Folder, Search And Sort Across Navigation&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The email detail page has a new “← Emails” link that takes you back to the list with your folder, search and email type still applied.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Deleting an email in a folder now keeps you in that folder, with the same view, search and sort. It used to take you back to the top level, or from the campaign list to the transactional list.&lt;/p&gt;&lt;h2&gt;Bugfixes&lt;/h2&gt;&lt;ul&gt;&lt;li&gt;A list that a segment is limited to can no longer be deleted, since deleting it made the segment reach your whole audience. The app names the segments using the list, and the API returns &lt;code class=&quot;changelog-code&quot;&gt;409 list_in_use&lt;/code&gt;.&lt;/li&gt;&lt;li&gt;Segments with an unsupported condition are now rejected when saved, and any already saved match no contacts instead of possibly all of them.&lt;/li&gt;&lt;li&gt;Fixed campaign activity not being archived before the 30-day event window closed. For campaigns whose events had already expired, the download now says there is no archive instead of returning an empty CSV.&lt;/li&gt;&lt;li&gt;An edited pagination link on the sandbox Events page can no longer show other users' sandbox email events.&lt;/li&gt;&lt;li&gt;The Reply-To address set on a campaign is now included in the sent email, so replies no longer go to the from address.&lt;/li&gt;&lt;li&gt;Re-adding a sending domain left over from an earlier, unfinished setup now works instead of failing with “already registered”. Verifying a domain shows a clear message for a conflict, and the API returns 409 instead of 500.&lt;/li&gt;&lt;li&gt;A sending domain with broken DNS, such as an expired parent domain, no longer makes its page fail with an Internal Server Error.&lt;/li&gt;&lt;li&gt;Fixed deleting a sending domain sometimes leaving it stuck in the account.&lt;/li&gt;&lt;li&gt;Fixed daily domain health checks stopping for a whole team because one of its domains had no creation date. The API now marks &lt;code class=&quot;changelog-code&quot;&gt;created_at&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;updated_at&lt;/code&gt; as nullable.&lt;/li&gt;&lt;li&gt;Emails sent over SMTP now show accented characters, older character sets such as Windows-1250, and embedded &lt;code class=&quot;changelog-code&quot;&gt;cid:&lt;/code&gt; images correctly. A broken message now gets a permanent &lt;code class=&quot;changelog-code&quot;&gt;554&lt;/code&gt; error, so mail clients stop retrying it.&lt;/li&gt;&lt;li&gt;API sends whose HTML contains a &lt;code class=&quot;changelog-code&quot;&gt;localhost&lt;/code&gt; or local network link, common in local development, are no longer rejected with a 403 error.&lt;/li&gt;&lt;li&gt;A temporary problem on our side now returns &lt;code class=&quot;changelog-code&quot;&gt;503 auth_unavailable&lt;/code&gt; with &lt;code class=&quot;changelog-code&quot;&gt;Retry-After&lt;/code&gt;, instead of rejecting a valid API key with &lt;code class=&quot;changelog-code&quot;&gt;401 Invalid API key&lt;/code&gt;.&lt;/li&gt;&lt;li&gt;Fixed a team's first simultaneous API sends returning a 500 error for emails that were sent, and the “first email sent” notice arriving more than once.&lt;/li&gt;&lt;li&gt;“Send a test email” on a draft campaign now sends what is currently in the editor, including unsaved changes, with merge tags filled from sample contact values.&lt;/li&gt;&lt;li&gt;Saving an email twice in quick succession, for example with a double-click, no longer fails and loses the change.&lt;/li&gt;&lt;li&gt;Fixed social icons and other premade images becoming broken links after their stored copy was deleted, for example in the file manager. Emails that broke before this fix need the image added again once.&lt;/li&gt;&lt;li&gt;Emails moved into a marketing or transactional folder now switch to that folder's type, so campaign emails no longer go missing from the marketing grid and campaign picker.&lt;/li&gt;&lt;li&gt;The Events page now opens on the roughly 10 days of events that are kept, instead of 14, so it no longer looks like events are missing. Date pickers on Events, Logs and Analytics no longer offer future days.&lt;/li&gt;&lt;li&gt;Free teams with a custom sending allowance now see that allowance on the dashboard and usage page, instead of “3,000 emails per month”.&lt;/li&gt;&lt;li&gt;Fixed the light-mode “Your HTML code” dialog in the editor's HTML block showing pink text on a pink background. Lettr's own HTML editors now follow light and dark mode too.&lt;/li&gt;&lt;/ul&gt;</content>
  </entry>
  <entry>
    <id>https://lettr.com/changelog/2026-08/</id>
    <title>Lettr changelog: August 2026</title>
    <link rel="alternate" type="text/html" href="https://lettr.com/changelog/2026-08/"/>
    <published>2026-08-31T00:00:00Z</published>
    <updated>2026-08-31T00:00:00Z</updated>
    <summary>Everything Lettr shipped in August 2026: 1 new feature, 10 improvements and 17 bugfixes.</summary>
    <content type="html">&lt;h2&gt;New features&lt;/h2&gt;&lt;h3&gt;Manage Email Preferences Page Replaces The Unsubscribe Screen&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The unsubscribe link in every email now opens a page where recipients choose their topics, pause emails or unsubscribe, instead of a screen that could only unsubscribe.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The page shows the recipient's current status (Subscribed, Paused, Unsubscribed or Not receiving emails), a checkbox for each topic, a pause of 30, 60 or 90 days, and the campaigns they recently received, each linked to its web version. One “Update preferences” button saves everything. Unticking every topic unsubscribes, after asking for a reason, and ticking topics again brings an unsubscribed recipient back.&lt;/p&gt;&lt;p&gt;Topic opt-outs and pauses are checked again just before each part of a campaign is sent, so a change made during a large send still counts. A full unsubscribe also removes the recipient from private topics for good, so subscribing again does not bring them back.&lt;/p&gt;&lt;p&gt;The page still opens when a link carries a broken parameter. Its limits count requests per contact, not per IP address, so security gateways that open links before delivery can't stop a real recipient from unsubscribing.&lt;/p&gt;&lt;p&gt;Pauses show in Audiences too: a Paused badge with its end date, a Paused filter (the Subscribed filter no longer includes paused contacts), and the status and a &lt;code class=&quot;changelog-code&quot;&gt;paused_until&lt;/code&gt; column in CSV exports. The API adds a &lt;code class=&quot;changelog-code&quot;&gt;paused_until&lt;/code&gt; field that can be &lt;code class=&quot;changelog-code&quot;&gt;null&lt;/code&gt;; &lt;code class=&quot;changelog-code&quot;&gt;status&lt;/code&gt; still reads &lt;code class=&quot;changelog-code&quot;&gt;subscribed&lt;/code&gt; for a paused contact, and nothing else changes.&lt;/p&gt;&lt;h2&gt;Improvements&lt;/h2&gt;&lt;h3&gt;Bulk Contacts Endpoint Accepts Per-Contact Properties, Lists And Topics&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;&lt;code class=&quot;changelog-code&quot;&gt;POST /audience/contacts/bulk&lt;/code&gt; now takes a list of contacts, each with its own properties, lists and topic subscriptions, and imports them in one call.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Importing contacts with their own properties used to take one request per contact, and more for topics, at 3 requests per second for each team. Ten thousand contacts with properties and two topics each took about 30,000 requests and almost three hours; the same import now takes about 10 requests and a few seconds.&lt;/p&gt;&lt;p&gt;The response includes the ids of the new contacts, so there is no need to page through the audience to find them. Rows that fail validation are skipped and listed in the response while the rest are imported, and &lt;code class=&quot;changelog-code&quot;&gt;update_existing&lt;/code&gt; updates the properties of contacts that already exist. Top-level &lt;code class=&quot;changelog-code&quot;&gt;properties&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;list_ids&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;topics&lt;/code&gt; apply to every row unless the row sets its own. A topic set to &lt;code class=&quot;changelog-code&quot;&gt;opt_out&lt;/code&gt; keeps a new contact out of a topic that would otherwise subscribe them automatically.&lt;/p&gt;&lt;p&gt;New &lt;code class=&quot;changelog-code&quot;&gt;POST&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;DELETE /audience/contacts/topics/bulk&lt;/code&gt; endpoints add and remove topics for many contacts at once, like the existing ones for lists. The old &lt;code class=&quot;changelog-code&quot;&gt;{emails, list_id, properties}&lt;/code&gt; request works exactly as before, so existing integrations and lettr-php 2.4.0 need no changes.&lt;/p&gt;&lt;h3&gt;Topic Opt-Outs In Bulk Imports Apply To Existing Contacts&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;An &lt;code class=&quot;changelog-code&quot;&gt;opt_out&lt;/code&gt; in a bulk import now unsubscribes an existing contact from that topic, whether or not &lt;code class=&quot;changelog-code&quot;&gt;update_existing&lt;/code&gt; is set.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Without &lt;code class=&quot;changelog-code&quot;&gt;update_existing&lt;/code&gt;, the opt-out used to be ignored: the request returned 201 with no error and the contact stayed subscribed. &lt;code class=&quot;changelog-code&quot;&gt;update_existing&lt;/code&gt; now only controls whether properties are updated, because withdrawing consent is not something a request option should override. Check any import that counted on opt-outs being ignored.&lt;/p&gt;&lt;p&gt;Topic changes made through the bulk endpoints are now also recorded in each contact's consent history, which they used to skip.&lt;/p&gt;&lt;h3&gt;The 50-Recipient Cap Now Counts Cc And Bcc&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The 50-recipient limit on sends now counts &lt;code class=&quot;changelog-code&quot;&gt;to&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;cc&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;bcc&lt;/code&gt; together, as the documentation always said.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Only &lt;code class=&quot;changelog-code&quot;&gt;to&lt;/code&gt; used to be limited, so one request could carry, and be billed for, any number of recipients. A request with more than 50 in total now returns a 422, and scheduled sends follow the same limit, so check how many recipients your integration puts on one send.&lt;/p&gt;&lt;h3&gt;API Sends Skip Unsubscribe Suppression By Default&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The API reference now states that &lt;code class=&quot;changelog-code&quot;&gt;options.transactional&lt;/code&gt; defaults to &lt;code class=&quot;changelog-code&quot;&gt;true&lt;/code&gt;, so an API send also goes to unsubscribed recipients unless it is set to &lt;code class=&quot;changelog-code&quot;&gt;false&lt;/code&gt;.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Sending has always worked this way; only the reference was missing it. Marketing emails sent through the API need &lt;code class=&quot;changelog-code&quot;&gt;options.transactional&lt;/code&gt; set to &lt;code class=&quot;changelog-code&quot;&gt;false&lt;/code&gt;.&lt;/p&gt;&lt;h3&gt;Adamko AI Assistant Available To Every Team&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adamko, the AI assistant, is now available to every team while it is in beta.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The chat panel now opens with its introduction only once for each team, instead of on every visit, and the onboarding banner on the dashboard can be dismissed for good.&lt;/p&gt;&lt;h3&gt;Adamko Creates API Keys And Sending Domains In Conversation&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adamko can now create an API key or add a sending domain when asked in chat, not only in the “Set up everything” scenario.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;In ordinary chat he used to refuse, with reasons that were not true, such as needing your domain registrar login. Adding a sending domain in Lettr never needs one.&lt;/p&gt;&lt;p&gt;He now takes the same steps as the setup scenario. An API key can be live or sandbox, with full or sending-only access. When a domain is already in use or blocked, he gives the real reason, and he still walks you through the DNS setup when you ask for that instead.&lt;/p&gt;&lt;h3&gt;Stop Button And Message Queue In The Adamko Chat&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A reply from Adamko can now be stopped while he is writing it, and a new message can be queued while he is still answering.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The message box used to stay locked until he finished. A stopped reply keeps the text already shown, and a queued message sends itself when the current reply ends. Work he has already started in the background, such as a brand kit or a set of emails, still finishes, and the stopped reply says so.&lt;/p&gt;&lt;h3&gt;Backoff Schedule For Repeat DNS Failure Alerts&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;With the default settings, a DNS record that stays broken now alerts on day 0, 1, 4 and 11 and then goes quiet, instead of alerting every day.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The domain still shows as failing in the app, and the summary email follows the same schedule. A record that newly breaks still alerts right away, and fixing a record starts the schedule again. The alert settings slider, now called “First repeat after”, sets the first gap; the next two are three and seven times as long.&lt;/p&gt;&lt;h3&gt;Move And Duplicate Folder Pickers Limited To The Email's Module&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The folder pickers for moving and duplicating an email now list only folders of the same kind, marketing or transactional.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Picking a folder of the other kind used to change the email's type without warning. The duplicate picker now opens on a folder (the email's own, the module's main folder or the first one offered) instead of an empty choice. Marketing email cards also get “Copy to Transactional”, and a copy made for the other module now goes into one of that module's folders.&lt;/p&gt;&lt;h3&gt;Documentation Link In The App Top Bar&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The top bar of the app now links straight to the documentation.&lt;/strong&gt;&lt;/p&gt;&lt;h2&gt;Bugfixes&lt;/h2&gt;&lt;ul&gt;&lt;li&gt;Confirmation and warning messages appear again after actions such as adding or deleting a domain, and editor settings no longer confirm a save twice.&lt;/li&gt;&lt;li&gt;Fixed the dashboard returning a 500 error for teams whose subscription no longer exists; they now see the free plan's limits.&lt;/li&gt;&lt;li&gt;Deleting a domain now removes its health alert from the dashboard, including alerts from earlier deletions, and old “Check domain” links open the domain list.&lt;/li&gt;&lt;li&gt;Fixed previewing a premade email in the Create Email dialog changing the look of the app behind it, with stretched thumbnails and a resized logo.&lt;/li&gt;&lt;li&gt;A closed Adamko panel now stays closed after a page reload or a new sign-in, even before onboarding is finished.&lt;/li&gt;&lt;li&gt;Fixed the Adamko chat opening on the first message instead of the latest one when reopened.&lt;/li&gt;&lt;li&gt;The “Drop your CSV to attach it” overlay in the Adamko chat no longer gets stuck and blocks the chat until the page is reloaded.&lt;/li&gt;&lt;li&gt;Fixed Adamko's suggested quick actions not updating, so “Help me set up my sending domain” stayed after a domain was already added.&lt;/li&gt;&lt;li&gt;“Set up everything” now creates the emails when the account has only one blank untitled draft, instead of reporting them as already created.&lt;/li&gt;&lt;li&gt;Brand kit logo detection no longer picks another site's logo from the page, such as a partner badge, over the site's own logo.&lt;/li&gt;&lt;li&gt;Brand kit logos now use the right light or dark version, and very light logos get a darker tile, instead of vanishing against the background.&lt;/li&gt;&lt;li&gt;Fixed brand kit logos sometimes showing as a broken image while emails were being generated.&lt;/li&gt;&lt;li&gt;Generated emails no longer include pink dividers or other colors from outside the brand; those now become a shade of the brand color.&lt;/li&gt;&lt;li&gt;Fixed brand kits with only one color producing generated emails with empty content blocks, large gaps and oversized rounded corners.&lt;/li&gt;&lt;li&gt;Campaign drafts that Adamko creates now go into a marketing folder instead of a transactional one.&lt;/li&gt;&lt;li&gt;Social icons in generated emails now turn white on dark or strongly colored footers, where the grey icons used to disappear.&lt;/li&gt;&lt;li&gt;A brand kit website that can't be read now gets a clear explanation and a prompt to try another address, instead of near-empty setup emails.&lt;/li&gt;&lt;/ul&gt;</content>
  </entry>
  <entry>
    <id>https://lettr.com/changelog/2026-07/</id>
    <title>Lettr changelog: July 2026</title>
    <link rel="alternate" type="text/html" href="https://lettr.com/changelog/2026-07/"/>
    <published>2026-07-24T00:00:00Z</published>
    <updated>2026-07-24T00:00:00Z</updated>
    <summary>Everything Lettr shipped in July 2026: 2 new features, 12 improvements and 18 bugfixes, including Daily DNS Health Checks For Verified Domains.</summary>
    <content type="html">&lt;h2&gt;New features&lt;/h2&gt;&lt;h3&gt;Daily DNS Health Checks For Verified Domains&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Verified domains are now checked once a day, with an alert when one stops resolving or stops pointing at Lettr.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A domain that verified months ago and broke later used to go unnoticed until sending failed. The check only reads DNS and never changes a domain's status, so it can't turn off a domain that is still sending.&lt;/p&gt;&lt;p&gt;Broken records show on the dashboard and as a badge on the domain, email and campaign lists, with the failing records and how long they have been failing. A newly broken record always sends an alert, a record already reported stays quiet for a while, and a team with several broken domains gets one email for all of them instead of one per domain.&lt;/p&gt;&lt;p&gt;The alert can be turned off in Settings → Alerts, which also sets the minimum time between repeat alerts for a failing record, from 1 to 720 hours.&lt;/p&gt;&lt;h3&gt;Activity Log And Undo For Changes Made By Adamko&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Every email, campaign, brand kit, sending domain, API key and contact property that Adamko creates or changes now appears in one Activity view, where anything he created can be undone.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Each entry shows the message that led to it, and a bulk action is one row with a count instead of one row per item. Entries stay in the log after the chat history is cleared or the item itself is deleted.&lt;/p&gt;&lt;p&gt;Undo is offered only while it is safe: a campaign must still be an untouched draft, an email must be unedited, a sending domain must not be verified yet, and an API key must still exist. A changed brand kit goes back to how it was before the change. When something can't be undone, the reason is shown, and the entry stays in the log either way.&lt;/p&gt;&lt;h2&gt;Improvements&lt;/h2&gt;&lt;h3&gt;Adamko Generates Branded Transactional Emails From Premade Bases&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adamko now picks the transactional emails that suit your product and builds each one from a Lettr premade in your brand's colors, fonts and logo.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The premades are already tested in email clients, and one design style is chosen for each team and kept, so its transactional emails and campaign drafts look alike. He can also build a single email from a description, such as an announcement or a newsletter, starting from the closest premade.&lt;/p&gt;&lt;p&gt;The text is now written in your website's language, subject lines included, where it used to be English. If a translation fails, the English version is kept rather than a half-translated one.&lt;/p&gt;&lt;p&gt;Emails are built in the background, and the chat shows a progress bar with a rough time estimate. The chosen emails appear in the Emails list right away with a Finalizing badge and can't be opened until they are finished.&lt;/p&gt;&lt;h3&gt;Brand Kit Extraction Reworked For Colors, Fonts And Inline SVG Logos&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Reading a brand kit from a website now finds the site's own colors, fonts and logo more reliably, instead of framework defaults, hover colors or fonts the page never uses.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Colors used only for hover, focus or selection now count for less, colors written by name (such as &lt;code class=&quot;changelog-code&quot;&gt;gold&lt;/code&gt;) are recognised, a CSS framework's built-in colors no longer outvote the brand, and a single decorative gradient no longer beats a color used across the site.&lt;/p&gt;&lt;p&gt;Fonts are ranked by what the site actually loads, not by every font a site builder lists in its stylesheet. Logos drawn straight into the page as SVG, with no image file behind them, are now found through the link back to the homepage and saved as a separate file.&lt;/p&gt;&lt;h3&gt;Adamko Read-Only Account Tools And Advisory Diagnostics&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adamko can now look up your plan and quota, emails, API keys, webhooks, team members, delivery events, API logs, contacts, imports and suppression list, and give advice based on what he finds.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;He used to answer many of these questions with “I cannot see that”. API keys are shown as details only, and the key itself is never returned. He can also check whether one particular recipient is on the suppression list.&lt;/p&gt;&lt;p&gt;Asked why an address didn't get an email, he gives one cause (suppressed, complained, hard bounced, blocked by the provider, delayed, rejected at send, still on its way, or delivered) with the evidence and what to do. Asked about failing API requests or webhooks, he lists the problems by severity, such as rejected keys, rate limits or a disabled webhook, with the steps to fix each one.&lt;/p&gt;&lt;p&gt;He checks an email for broken merge tags, a missing unsubscribe link, images without alt text, fixed widths that break on phones, a size Gmail will clip and subject lines likely to look like spam. He also compares recent campaigns, suggests a list or segment for a goal, and plans lifecycle emails or a campaign calendar within the sending quota you have left. Rates with nothing to calculate from show as unknown instead of 0%, and he never claims to have scheduled anything, since none of his tools can.&lt;/p&gt;&lt;h3&gt;Adamko CSV Import Review And Column Mapping&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A CSV file dropped on the Adamko chat now goes straight to the contact import, and the file itself is never sent to the AI.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;When columns are left unmapped, “Ask Adamko” on the mapping step lists what is wrong with the file (no email column, invalid addresses, duplicates in the file, contacts you already have, no consent information or unknown statuses), quoting the values it found. “Map them for me” first shows which custom fields will be created and with what type, which existing fields are reused and how the status column will be read. Each field he creates can be undone from the activity log.&lt;/p&gt;&lt;p&gt;After the import, he can suggest segments based on the mapped columns. The mapping step now also offers “Subscription status” as a field, where it used to offer only the email address.&lt;/p&gt;&lt;h3&gt;Secret And Personal Data Redaction For Every AI Request&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Every AI feature in Lettr now removes secrets and recipient details from a request before it goes to the AI, where this used to depend on the feature.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;API keys, bearer tokens, private keys and long secret-looking strings are masked for good, in your messages, the chat history and tool results alike. Recipient details inside email HTML are swapped for placeholders that are put back in the response, so an email edited with AI comes back complete.&lt;/p&gt;&lt;p&gt;Details in ordinary conversation are left as they are, since a question about why mail to a named address bounced needs that address; this is covered in the data processing agreement. Two older AI chat features in the email editor now follow the same access rules, rate limit and monthly spending cap as Adamko.&lt;/p&gt;&lt;h3&gt;Proactive Adamko Notices For Five Account Problems&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adamko now shows a notice on the relevant page, without being asked, for a failing domain, a sudden rise in bounces, a stalled setup, a missing API key or a draft he started that was left unfinished.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Each page shows at most one notice. A dismissed notice stays hidden for 3 to 14 days depending on its type, a domain notice dismissed by one teammate is hidden for the whole team, and dismissing three notices in a week hides them all for a while.&lt;/p&gt;&lt;h3&gt;Complete DNS Walkthroughs For Sending, Tracking, Inbound And Storage Domains&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adamko's add-domain walkthrough now covers every DNS record and the verification step, where it used to stop after the first record.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;It goes through DKIM, CNAME, SPF, DMARC and verification in order, and skips any record a domain type doesn't have instead of stalling on it. Tracking, inbound and storage domains got the same walkthroughs; storage domains had none. A record step now finishes when you copy its value, not only when you click the text, and the API key walkthrough has a new step for choosing a sandbox key.&lt;/p&gt;&lt;h3&gt;Section Links, Copy Button And Tables In Adamko Answers&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;When Adamko names a section of the app in an answer, he now offers a link to it instead of only putting the name in bold.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;These links, and the “Guide me” and “Docs” buttons, stay clickable in later messages and after a page reload; they used to disappear with the next message. Every answer has a Copy button, tables show as tables instead of rows of &lt;code class=&quot;changelog-code&quot;&gt;|&lt;/code&gt; characters, and the message box grows as you type.&lt;/p&gt;&lt;h3&gt;Adamko Onboarding Cards Persist Across Page Reloads&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The cards in Adamko's replies (the brand kit preview, the email picker, the API key and the domain) now stay after a page reload, where they used to be replaced by plain text.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;They come back in their finished state: a restored API key card is masked and has no copy button, and the key itself is still never saved. The email picker now says how many of the available emails it will create, for example “Create 4 of 7 emails”, and shows that more options are further down the list.&lt;/p&gt;&lt;h3&gt;Per-Source Data Windows For Adamko Sending Health Answers&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adamko's answers about sending health now use the time range each data source actually keeps, instead of claiming 90 days for everything.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Questions reaching past the roughly 10 days of kept message events used to fail with “something went wrong on my side”. Trends still cover the full period, while recent examples cover only what is kept and say so. When the examples can't be loaded, the answer still comes back without them.&lt;/p&gt;&lt;h3&gt;Synced Section Edits Create New Email Versions&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Editing a synced header or footer now saves a new version of every email that uses it, instead of overwriting those emails in place.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The editor then offers to publish them all at once, or to keep them as drafts to check first.&lt;/p&gt;&lt;h3&gt;New Marketing Emails Open Directly In The Editor&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Creating a marketing email now opens it straight in the editor, without the detail page in between.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;After saving, the newest version is shown instead of an older one, and the folder picker on the emails page offers only folders of the kind being browsed.&lt;/p&gt;&lt;h2&gt;Bugfixes&lt;/h2&gt;&lt;ul&gt;&lt;li&gt;Fixed one-time codes being rejected as invalid or expired for everyone, which blocked password and email changes, two-factor setup and team deletion.&lt;/li&gt;&lt;li&gt;Requesting a new one-time code right after verifying one now sends a working code, instead of reporting success without creating one.&lt;/li&gt;&lt;li&gt;One-time code emails no longer arrive after the code has expired when a lot of other mail is waiting to be sent.&lt;/li&gt;&lt;li&gt;Deleting a folder no longer deletes the emails inside it; they now move to another folder of the same kind.&lt;/li&gt;&lt;li&gt;A marketing email moved into a folder no longer also shows at the top level, where it looked like a duplicate.&lt;/li&gt;&lt;li&gt;Fixed duplicating a marketing email always creating a transactional copy, which left the copy missing from the campaigns list.&lt;/li&gt;&lt;li&gt;Open rates on the dashboard and in tag stats no longer go above 100%.&lt;/li&gt;&lt;li&gt;Fixed a double-click on Sign up creating two accounts or showing a server error.&lt;/li&gt;&lt;li&gt;The screen no longer flashes and the Adamko panel no longer jumps each time he takes you to another page.&lt;/li&gt;&lt;li&gt;The editor's file manager now lists every file in a folder that holds more than 1,000 files, not only the first 1,000.&lt;/li&gt;&lt;li&gt;Fixed files in the editor's file manager coming back after a delete that was reported as successful.&lt;/li&gt;&lt;li&gt;Files uploaded from inside a subfolder of the editor's file manager now go into that subfolder, not a new folder at the top level.&lt;/li&gt;&lt;li&gt;Pasting a link into the Adamko chat no longer returns “please try again in a moment”; he now says he can't open web pages.&lt;/li&gt;&lt;li&gt;Fixed Adamko mentioning the names of his internal tools, such as &lt;code class=&quot;changelog-code&quot;&gt;get_brand_kit&lt;/code&gt;, in his replies.&lt;/li&gt;&lt;li&gt;Walkthrough replies from Adamko no longer end with the same closing sentence twice.&lt;/li&gt;&lt;li&gt;In replies not written in English, the closing “Guide me” button no longer merges into the paragraph above it.&lt;/li&gt;&lt;li&gt;Fixed the campaigns list not scrolling, which left campaigns further down the list out of reach.&lt;/li&gt;&lt;li&gt;The email preview no longer shrinks to nothing when the window is too narrow to show it side by side.&lt;/li&gt;&lt;/ul&gt;</content>
  </entry>
  <entry>
    <id>https://lettr.com/changelog/2026-06/</id>
    <title>Lettr changelog: June 2026</title>
    <link rel="alternate" type="text/html" href="https://lettr.com/changelog/2026-06/"/>
    <published>2026-06-09T00:00:00Z</published>
    <updated>2026-06-09T00:00:00Z</updated>
    <summary>Everything Lettr shipped in June 2026: 3 new features, 10 improvements and 18 bugfixes, including Transactional And Marketing Mode Switcher In The Sidebar.</summary>
    <content type="html">&lt;h2&gt;New features&lt;/h2&gt;&lt;h3&gt;Transactional And Marketing Mode Switcher In The Sidebar&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The sidebar now opens with a Transactional and Marketing mode switcher, and the menu below it shows only what that mode uses.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Both sets of navigation used to share one sidebar. Marketing mode adds Audience and Campaigns, and its Emails list shows only marketing emails. Switching mode on the Emails page shows the other mode's emails, and switching away from a marketing-only page such as Audience or Campaigns opens the dashboard.&lt;/p&gt;&lt;p&gt;A shared link always opens in the right mode, whichever mode the person opening it used last, and the chosen mode stays set between sessions. Analytics and Events now sit together under Metrics.&lt;/p&gt;&lt;p&gt;The new layout also adds a top bar, a team switcher at the bottom of the sidebar and a proper menu drawer on mobile, where the app used to show a narrower copy of the desktop sidebar.&lt;/p&gt;&lt;h3&gt;Adamko AI Assistant With Account Tools And Guided Setup&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adamko is a new AI assistant in the app that can look at your account, make changes in it and guide you through its pages.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Asked which sending domains are ready to send, he lists them with the same readiness badge the Domains page shows. Asked why a domain is not verifying, he checks its live DNS records against what the provider reports and names the actual mistake: a record at the wrong host, two SPF records, a CNAME flattened or proxied by Cloudflare, DMARC on the wrong host or a typo in the value. He only calls a record correct after checking it in the same reply, and he quotes every host and value exactly.&lt;/p&gt;&lt;p&gt;When the answer is a page in the app, he opens it instead of describing the way there. He can also point to each step on the real page, for creating a sending domain or an API key, building a list or a segment, adding a webhook, or finding the events for one recipient.&lt;/p&gt;&lt;p&gt;Onboarding now runs through him and replaces the old checklist. Given your website, he reads it, shows what he found, creates the transactional emails you pick, then creates an API key and adds a sending domain. He finishes with a walkthrough of the DNS records, since verification still depends on your registrar and on the DNS changes spreading.&lt;/p&gt;&lt;p&gt;His tools follow the same permissions as the matching pages, so chat can't do anything your role doesn't allow in the app. Every action he takes is recorded in an audit log with sensitive values removed, and an API key he creates appears only in its own card, never in the chat history. He doesn't use emoji. Adamko is in beta and is being turned on team by team.&lt;/p&gt;&lt;h3&gt;Notification Centre In The App Top Bar&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A bell in the app top bar now collects notifications about things that finish while you are elsewhere in Lettr.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A finished campaign send shows its recipient count and links to the campaign, and a finished contacts export links to its download, which expires after one hour. Announcements from us arrive here too, instead of by email. Notifications can be marked as read one at a time or all at once.&lt;/p&gt;&lt;h2&gt;Improvements&lt;/h2&gt;&lt;h3&gt;Audience And Campaigns Enabled For Every Team&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Audience and Campaigns are now available to every team, instead of being turned on team by team.&lt;/strong&gt;&lt;/p&gt;&lt;h3&gt;Separate Dashboard Metrics For Transactional And Marketing Mode&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The dashboard now shows different cards and numbers in transactional and marketing mode, where it used to show one set for everything.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;In transactional mode, the usage card counts emails against your email limit and the analytics table groups sends by tag. In marketing mode, it counts contacts against your contact limit, the traffic chart shows a bar on each campaign's send date, delivery performance adds click and unsubscribe rates, and the table has one row per campaign.&lt;/p&gt;&lt;p&gt;Transactional numbers leave out campaign sends but still count sends that have no tag, and those now appear in their own Untagged row.&lt;/p&gt;&lt;h3&gt;Card Grid View For Marketing Emails&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Marketing emails now show as folders and thumbnail cards, with a toggle back to the table view.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Folders now belong to either marketing or transactional emails, and the marketing table hides the columns that only apply to transactional emails (slug, sent, opened and open rate). The transactional email list is unchanged.&lt;/p&gt;&lt;h3&gt;Two-Column Layout For The Transactional Email Page&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The transactional email page now has its settings on the left and a preview on the right, with desktop and mobile tabs and a language selector.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Name and subject save as you type, and the settings panel also shows the slug and the email's merge tags. The version status now sits in the header and turns green when a version is live, and version history opens in a drawer over the page instead of a separate view.&lt;/p&gt;&lt;h3&gt;Copy To Marketing And Copy To Transactional Email Actions&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Each email in the list now has a “Copy to Marketing” or “Copy to Transactional” action that copies it to the other mode.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The copy stays in the same folder, so an email designed for one mode no longer has to be rebuilt for the other.&lt;/p&gt;&lt;h3&gt;Three-Day Sessions And An Expiry Warning In The Email Editor&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The email editor now notices an expired session and offers to sign you back in before unsaved work is lost.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;An expired session used to show up only as a failed save. Sessions now also last three days instead of two hours, so being signed out while editing is much less likely. The editor also uses Lettr's own colors now.&lt;/p&gt;&lt;h3&gt;Warning State For Incomplete Steps In The Campaign Stepper&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A campaign step that has been passed but still has unresolved issues now shows a warning instead of a green tick.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The step navigation also moved into the top bar.&lt;/p&gt;&lt;h3&gt;X-Correlation-Id Header On Every API Response&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Every API response now includes an &lt;code class=&quot;changelog-code&quot;&gt;X-Correlation-Id&lt;/code&gt; header, and requests that end in an unexpected error are now logged.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Those requests used to leave no log entry. The API log page has new account and correlation id filters, so one id is enough to trace a failing request between your side and ours.&lt;/p&gt;&lt;h3&gt;Brand Impersonation Screening For New Sending Domains&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;New sending domains are now checked for names that imitate a well-known brand, such as a swapped digit or a lookalike spelling.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A clear lookalike is created as blocked, with a banner on the Domains page saying so, and a borderline one goes to our team for review. If the check itself fails, the domain is created as usual.&lt;/p&gt;&lt;h3&gt;Clearer Messages For Domains Registered Elsewhere And Cancelled Domain Connect Setup&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Adding a sending domain that an account outside Lettr has already registered with the provider now says so and asks you to contact support, instead of failing with a general error.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Cancelling the one-click Cloudflare setup no longer looks like success. The sending, inbound and tracking domain pages now show that the setup was cancelled.&lt;/p&gt;&lt;h2&gt;Bugfixes&lt;/h2&gt;&lt;ul&gt;&lt;li&gt;A team can no longer send from another team's verified sending domain, which is now refused with the same error as an unknown domain.&lt;/li&gt;&lt;li&gt;Fixed the campaign preview returning any team's campaign HTML to any signed-in user; it now checks that the campaign belongs to their team.&lt;/li&gt;&lt;li&gt;Fixed a request logger recording far more of each request than intended. It now hides authorization, cookie and API key headers and skips request bodies.&lt;/li&gt;&lt;li&gt;Our internal log of API requests now keeps only non-sensitive fields, so recipient addresses, content, attachments, substitution data, metadata and headers are never stored.&lt;/li&gt;&lt;li&gt;Fixed any signed-in user being able to create, edit or delete the premade blocks shown in every team's editor; this now needs an administrator.&lt;/li&gt;&lt;li&gt;Sending many emails at the same moment can no longer go over a plan's daily or monthly limit. Close to the limit, a send may occasionally be refused slightly early.&lt;/li&gt;&lt;li&gt;Password reset, email verification and team invitation links in Lettr's own emails now work, instead of arriving broken.&lt;/li&gt;&lt;li&gt;Fixed password reset links failing when the email address in the link arrived encoded, for example with &lt;code class=&quot;changelog-code&quot;&gt;%40&lt;/code&gt; in place of &lt;code class=&quot;changelog-code&quot;&gt;@&lt;/code&gt;.&lt;/li&gt;&lt;li&gt;A failed sign-in now shows its error message, and the email address typed there carries over to the password reset form.&lt;/li&gt;&lt;li&gt;API sends whose HTML contains a link with an IP address, such as &lt;code class=&quot;changelog-code&quot;&gt;http://192.168.1.50/status&lt;/code&gt;, are no longer rejected with a 403 error.&lt;/li&gt;&lt;li&gt;Fixed large bursts of delivery events from the provider being refused on our side with 429 errors.&lt;/li&gt;&lt;li&gt;The Events and message detail pages no longer fail on events that arrive without a transmission id or recipient details.&lt;/li&gt;&lt;li&gt;A tracking domain behind the Cloudflare proxy is no longer shown as verified. Set its record to DNS only in Cloudflare so it can verify.&lt;/li&gt;&lt;li&gt;The short links &lt;code class=&quot;changelog-code&quot;&gt;/domains&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;/logs&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;/templates&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;/suppressions&lt;/code&gt; used in our documentation now redirect to the right pages instead of returning 404.&lt;/li&gt;&lt;li&gt;Creating a new list from inside the CSV import flow now works instead of failing.&lt;/li&gt;&lt;li&gt;The emails list scrolls again instead of being cut off, and the sidebar no longer shows a scrollbar it doesn't need.&lt;/li&gt;&lt;li&gt;Successful statuses in the API log and webhook lists now show in green instead of the wrong color.&lt;/li&gt;&lt;li&gt;Fixed a sidebar section staying highlighted next to the more specific page open inside it.&lt;/li&gt;&lt;/ul&gt;</content>
  </entry>
  <entry>
    <id>https://lettr.com/changelog/2026-05/</id>
    <title>Lettr changelog: May 2026</title>
    <link rel="alternate" type="text/html" href="https://lettr.com/changelog/2026-05/"/>
    <published>2026-05-27T00:00:00Z</published>
    <updated>2026-05-27T00:00:00Z</updated>
    <summary>Everything Lettr shipped in May 2026: 2 new features, 12 improvements and 9 bugfixes, including Campaign Send, Schedule And Stats Endpoints In The API.</summary>
    <content type="html">&lt;h2&gt;New features&lt;/h2&gt;&lt;h3&gt;Campaign Send, Schedule And Stats Endpoints In The API&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Campaigns can now be listed, read, sent, scheduled, rescheduled and unscheduled through the API, with their events and stats.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Six endpoints use two new scopes, &lt;code class=&quot;changelog-code&quot;&gt;campaigns:read&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;campaigns:write&lt;/code&gt;. Every campaign includes a &lt;code class=&quot;changelog-code&quot;&gt;stats&lt;/code&gt; object with injections, deliveries, bounces, complaints, opens, unique opens, clicks, unique clicks and unsubscribes, the same numbers the app shows. &lt;code class=&quot;changelog-code&quot;&gt;GET /campaigns/{id}/events&lt;/code&gt; returns events page by page and filters by event type, recipient and date range.&lt;/p&gt;&lt;p&gt;A draft can be scheduled, and a scheduled campaign can be moved to a new time with the same call. Sending right away still needs a draft without a send time: a campaign that has one returns &lt;code class=&quot;changelog-code&quot;&gt;campaign_has_pending_schedule&lt;/code&gt;, which points to &lt;code class=&quot;changelog-code&quot;&gt;POST /campaigns/{id}/unschedule&lt;/code&gt;.&lt;/p&gt;&lt;p&gt;There is no endpoint for creating a campaign or choosing its audience. Campaigns are still created in the app, and the API works with them from there.&lt;/p&gt;&lt;h3&gt;Web Version Merge Tag For Viewing Campaigns In A Browser&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The new &lt;code class=&quot;changelog-code&quot;&gt;{{webversion_link}}&lt;/code&gt; merge tag gives each recipient their own link to view the campaign in a browser.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The page fills in that recipient's own details, so it matches the email they received. The tag is in the editor's merge-tag menu next to &lt;code class=&quot;changelog-code&quot;&gt;{{unsubscribe_link}}&lt;/code&gt;, and in test emails it opens a preview.&lt;/p&gt;&lt;h2&gt;Improvements&lt;/h2&gt;&lt;h3&gt;Audience API Write Endpoints Replace Three Nested Routes&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The audience API can now create, update and delete segments, topics and properties, update lists and contacts, and create contacts in bulk.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A contact can be added to or removed from a list or a topic, and lists can also be added to or removed from many contacts at once, or deleted in bulk. Writes need the &lt;code class=&quot;changelog-code&quot;&gt;audience:write&lt;/code&gt; scope and don't work with sandbox API keys; reads need &lt;code class=&quot;changelog-code&quot;&gt;audience:read&lt;/code&gt;.&lt;/p&gt;&lt;p&gt;Three nested endpoints were removed in favour of filters. &lt;code class=&quot;changelog-code&quot;&gt;GET /audience/lists/{id}/contacts&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;GET /audience/segments/{id}/contacts&lt;/code&gt; are now &lt;code class=&quot;changelog-code&quot;&gt;GET /audience/contacts?list_id=&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;?segment_id=&lt;/code&gt;, and &lt;code class=&quot;changelog-code&quot;&gt;GET /audience/lists/{id}/segments&lt;/code&gt; is now &lt;code class=&quot;changelog-code&quot;&gt;GET /audience/segments?list_id=&lt;/code&gt;.&lt;/p&gt;&lt;p&gt;The contacts list response changed from &lt;code class=&quot;changelog-code&quot;&gt;{contacts, total, page, per_page}&lt;/code&gt; to &lt;code class=&quot;changelog-code&quot;&gt;{contacts, pagination: {…}}&lt;/code&gt;, and the lists inside a contact no longer include &lt;code class=&quot;changelog-code&quot;&gt;contacts_count&lt;/code&gt;. Check these changes in any integration built before May.&lt;/p&gt;&lt;h3&gt;Topic Opt-In And Opt-Out Defaults Corrected&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A topic set to &lt;code class=&quot;changelog-code&quot;&gt;opt_out&lt;/code&gt; now subscribes new contacts automatically and &lt;code class=&quot;changelog-code&quot;&gt;opt_in&lt;/code&gt; requires them to subscribe, the reverse of how both used to work.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The setting was implemented backwards, and the app's own descriptions matched the wrong behaviour. The fix applies to contacts created through the API, CSV import and the app.&lt;/p&gt;&lt;p&gt;Stored topics were not changed, so every existing topic now behaves the opposite way from before. Check the setting on every topic before the next send.&lt;/p&gt;&lt;h3&gt;Segment AND And OR Rules Corrected In The API Reference&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The API reference now says conditions within a group are joined by OR and groups by AND, which is how segments have always worked.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The reference used to say the opposite. Only the text was wrong: segments and the app's own labels always worked this way, so existing segments have not changed and don't need saving again.&lt;/p&gt;&lt;p&gt;Segments built by following the reference instead of the segment builder match the opposite of what was intended, so check them. We're sorry for the time this cost.&lt;/p&gt;&lt;h3&gt;Automatic Unsubscribe Footer And List-Unsubscribe Headers On Campaigns&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Every campaign now has an unsubscribe link and one-click unsubscribe headers, even when the email has no unsubscribe tag.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;When the HTML contains neither &lt;code class=&quot;changelog-code&quot;&gt;{{unsubscribe_link}}&lt;/code&gt; nor &lt;code class=&quot;changelog-code&quot;&gt;{{unsubscribe_url}}&lt;/code&gt;, a short footer is added at sending time, and the saved email is not changed. Every campaign also sets &lt;code class=&quot;changelog-code&quot;&gt;List-Unsubscribe&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;List-Unsubscribe-Post&lt;/code&gt;, so the one-click unsubscribe button works in Gmail and Apple Mail.&lt;/p&gt;&lt;p&gt;The footer can't be turned off; adding your own unsubscribe tag is the way to replace it. The campaign editor shows a banner with an “Insert link” button when the tag is missing, and warns before saving an email without one.&lt;/p&gt;&lt;h3&gt;Unsubscribe Confirmation Page With Reasons And Resubscribe&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The unsubscribe link in an email now opens a page that asks for confirmation, instead of unsubscribing the recipient as soon as the page loads.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Recipients can pick a reason (too many emails, not relevant, never signed up, or their own text), which is saved in the contact's history. After unsubscribing, the page offers a one-click way to subscribe again, since many of these clicks are accidents.&lt;/p&gt;&lt;p&gt;The one-click unsubscribe in the mail client still unsubscribes right away, as the standard requires.&lt;/p&gt;&lt;h3&gt;Unsubscribe And Web Version Pages In 19 Languages&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The unsubscribe and web version pages now show in the recipient's language, in 19 languages, where they used to be English only.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The language comes from the contact's communication language, then from a team default the owner sets in Team settings → Overview, then English. Only the page around the email is translated: the email itself is shown as written, and the default unsubscribe footer added to campaigns stays in English.&lt;/p&gt;&lt;p&gt;Arabic and Hebrew are not included yet, because the pages don't support right-to-left text. Unsubscribe reasons are saved the same way whatever language the recipient saw, so they can be compared across languages.&lt;/p&gt;&lt;h3&gt;Emailed Confirmation Codes For Sensitive Actions On SSO Accounts&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Accounts that sign in with Google or GitHub now confirm sensitive actions with a six-digit code sent by email.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;These accounts used to skip the check entirely when changing the password or account email, turning two-factor authentication on or off, or deleting the user or a team. The code is valid for 10 minutes, and one confirmation covers all of these actions for 15 minutes. Accounts with a password still confirm with it.&lt;/p&gt;&lt;p&gt;Changing the account email now sends the verification email again; it used to mark the account unverified with nothing to click. Password fields on sign-up, password reset and settings also show a live checklist of the rules: at least 12 characters, upper and lower case, a number and a symbol.&lt;/p&gt;&lt;h3&gt;Campaign Test Sends Use The Production Sending Path&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Campaign test sends now go through the same sending path as the real campaign, so they show what recipients will get.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Tracking is on, and the unsubscribe and web version links work, opening preview pages that change nothing. The “Send test” button in the editor opened from a campaign now uses the same path; it used to send without the unsubscribe footer or web version link, and with the wrong sender and subject.&lt;/p&gt;&lt;h3&gt;Boolean Segment Conditions No Longer Require A Value&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Segment conditions on true/false properties (&lt;code class=&quot;changelog-code&quot;&gt;is_true&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;is_false&lt;/code&gt;) no longer require a &lt;code class=&quot;changelog-code&quot;&gt;value&lt;/code&gt;.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Every condition used to require one, so a condition on a true/false property was rejected, both through the API and in the app's segment builder.&lt;/p&gt;&lt;h3&gt;Plan Contact Limit Check Before A Campaign Is Sent&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The campaign editor now shows an “Upgrade required to send” dialog with your contact count and plan limit when a send would go over the limit, instead of failing during the send.&lt;/strong&gt;&lt;/p&gt;&lt;h3&gt;Duplicate Action For Segments&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The row menu on the Segments list has a new Duplicate action that copies a segment's conditions and list, then opens the copy.&lt;/strong&gt;&lt;/p&gt;&lt;h3&gt;CSV And JSON Export Of Domain DNS Records&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A new “Send to developer” menu on each domain page downloads the DNS records the domain needs as CSV or JSON.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;It works for sending, tracking, inbound and storage domains, and uses the domain's own values from the page.&lt;/p&gt;&lt;h2&gt;Bugfixes&lt;/h2&gt;&lt;ul&gt;&lt;li&gt;CSV imports separated by semicolons, tabs or pipes now map their columns, instead of arriving as one column with nothing mapped.&lt;/li&gt;&lt;li&gt;Fixed new segments saving without their conditions, so every segment created since March had to be opened and saved a second time.&lt;/li&gt;&lt;li&gt;Opening the email editor from a campaign no longer loses the subject, sender, audience and schedule entered before it.&lt;/li&gt;&lt;li&gt;Fixed the “Send campaign” button doing nothing when an ad blocker was running in the browser.&lt;/li&gt;&lt;li&gt;Creating a contact with double opt-in and a missing or unpublished template no longer creates the contact without sending a confirmation. The API now returns 404 &lt;code class=&quot;changelog-code&quot;&gt;template_not_found&lt;/code&gt;, or 502 &lt;code class=&quot;changelog-code&quot;&gt;transmission_failed&lt;/code&gt; when sending fails, instead of 500.&lt;/li&gt;&lt;li&gt;The DNS provider guide buttons on the sending, tracking and inbound domain pages now open the right guides instead of missing pages.&lt;/li&gt;&lt;li&gt;The campaign preview dialog now shows the whole email instead of shrinking to a strip with only its top.&lt;/li&gt;&lt;li&gt;Fixed the action buttons in the domain page header running off narrow screens instead of wrapping below the title.&lt;/li&gt;&lt;li&gt;The divider between the sidebar and the page now shows in dark mode.&lt;/li&gt;&lt;/ul&gt;</content>
  </entry>
  <entry>
    <id>https://lettr.com/changelog/2026-04/</id>
    <title>Lettr changelog: April 2026</title>
    <link rel="alternate" type="text/html" href="https://lettr.com/changelog/2026-04/"/>
    <published>2026-04-29T00:00:00Z</published>
    <updated>2026-04-29T00:00:00Z</updated>
    <summary>Everything Lettr shipped in April 2026: 1 new feature, 12 improvements and 14 bugfixes, including Email Campaigns With Scheduling And Per-Recipient Results.</summary>
    <content type="html">&lt;h2&gt;New features&lt;/h2&gt;&lt;h3&gt;Email Campaigns With Scheduling And Per-Recipient Results&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Lettr can now send campaigns: write the email, choose an audience, send it now or at a set time, and see the results for each recipient.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A campaign is set up in four steps: Compose, Audience, Schedule, and Review and Send. A step counts as done only when it is complete, a problem shows on the step it belongs to, and each item on the review list jumps to its step and field. “New campaign” opens the editor straight away, and the campaign's name follows its subject line until you change it. The email can be written in the Topol editor or in raw HTML, and the preview shows the campaign as it is now instead of a saved screenshot. A reopened draft lets you move between steps freely, and everything is still checked before sending.&lt;/p&gt;&lt;p&gt;The From address is the part before the @ plus a list of your verified sending domains, so a campaign can't be set up with an address it can't send from. Test sends go out the same way as the real campaign, with open and click tracking off so they don't count in its results, and each team can send 10 an hour. A scheduled campaign is sent at the time you picked and can be moved back to draft until then.&lt;/p&gt;&lt;p&gt;The results page shows unique opens and clicks, counted once per recipient. Every rate is measured against the total number of recipients, so campaigns can be compared with each other, and a tooltip says so. The number tiles also filter the recipient list: Bounced lists the bounced recipients with the full bounce reason. While a campaign prepares and sends, the page updates by itself, and it keeps updating for a while after sending, with a banner saying it is waiting for delivery events.&lt;/p&gt;&lt;p&gt;Activity for each recipient is kept for 30 days. Just before it expires, each campaign's events are archived, and the campaign page can email you a download link; the activity view offers it once the history is older than 30 days. Select two or more campaigns to compare them side by side, with the best and worst result for each metric marked, or to delete or duplicate them together.&lt;/p&gt;&lt;h2&gt;Improvements&lt;/h2&gt;&lt;h3&gt;Separate Audience Tabs For Lists And Segments With Live Segment Preview&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Lists and Segments now have their own tabs in Audience, next to Contacts, Topics and Properties.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;All five tabs share the same filters, table and empty states. Active filters show as chips that can be cleared, the number cards at the top filter by status, and a contact opens in a side panel, so editing it doesn't lose your place in the list. The contacts table has new Topics, Lists and Segments columns that filter the list when clicked, shows 25, 50, 100 or 150 contacts per page, and an empty tab now says whether nothing exists yet or nothing matched the filters.&lt;/p&gt;&lt;p&gt;The segment builder now shows the matching contacts and their count while the conditions are being written. It used to show them only after “Save &amp;amp; preview”.&lt;/p&gt;&lt;h3&gt;Activity Log On The Contact Detail Page&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Each contact's page now has an activity log recording when the contact was created and every change to its lists, topics, properties, email address and status.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Names are saved as they were at the time, so the log still shows a list or topic by name after it is deleted.&lt;/p&gt;&lt;h3&gt;Inline Editing For Contacts, Topics And Property Fallback Values&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;An Edit contact panel on the contact's page now changes its email address, status, lists and topics in one place.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Topics now have an editable name, description and visibility. A topic's default subscription can't be changed after the topic is created, because contacts were already subscribed or not based on it. For properties, the fallback value can now be edited, with an input that matches the property's type.&lt;/p&gt;&lt;h3&gt;Bulk Actions For Contacts, Lists, Segments, Topics And Properties&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Selected contacts can now be deleted, subscribed, unsubscribed, or added to and removed from lists and topics all at once.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The actions match the selection. Subscribe and Unsubscribe are turned off when every selected contact already has that status, and the list and topic pickers show whether all, some or none of the contacts are in each one, so after filtering by a list the picker offers to remove the contacts from it instead of adding them again. Topics, properties, segments and lists can be deleted in bulk too.&lt;/p&gt;&lt;h3&gt;List-Scoped Contact Exports With A Recent Exports Panel&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Exporting contacts from inside a list now exports only that list, where it used to export your whole audience.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Large audiences now export without running out of memory. A Recent exports panel shows the last five exports from the past 24 hours and updates as each one finishes. The download link is sent only by email, never shown in the browser, and each user can start up to 20 exports an hour.&lt;/p&gt;&lt;h3&gt;Purpose Field Separates Campaign Emails From Transactional Emails&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Every email now has a purpose, so the Emails list shows only transactional emails and the campaign builder shows only campaign emails.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Campaign drafts used to appear among transactional emails. The purpose is set when an email is created and can't be changed later. Emails created through the API or MCP are always transactional, and those endpoints don't accept the field, so existing integrations work as before.&lt;/p&gt;&lt;h3&gt;Default Bounce Domain Switch On Sending Domains&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A verified sending domain can now be made the team's default bounce domain with a switch on the domain's page.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The switch stays off until the domain's CNAME record is verified, with the hint “Verify the CNAME record before enabling”, instead of failing after it is turned on.&lt;/p&gt;&lt;h3&gt;Webhook Event Types Renamed From Engagament To Engagement&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The six webhook engagement event types, published as &lt;code class=&quot;changelog-code&quot;&gt;engagament.*&lt;/code&gt;, are now spelled &lt;code class=&quot;changelog-code&quot;&gt;engagement.*&lt;/code&gt;.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The old spelling is still accepted everywhere, so webhooks subscribed under it keep working. Update any code that matches on the event name.&lt;/p&gt;&lt;h3&gt;Webhooks API Accepts Fully-Prefixed Event Names On Create&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Creating a webhook now accepts the full event names that the webhook response returns, such as &lt;code class=&quot;changelog-code&quot;&gt;message.delivery&lt;/code&gt;, as well as the short form &lt;code class=&quot;changelog-code&quot;&gt;delivery&lt;/code&gt;.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;code class=&quot;changelog-code&quot;&gt;url&lt;/code&gt; is now the main field for the webhook address, and &lt;code class=&quot;changelog-code&quot;&gt;target&lt;/code&gt; is still accepted on update. A webhook subscribed to every event now returns &lt;code class=&quot;changelog-code&quot;&gt;event_types: null&lt;/code&gt;, the all-events form the API reference describes, instead of a list of every event.&lt;/p&gt;&lt;h3&gt;Warning-Level Fields Removed From The Domain Verification Response&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Four undocumented &lt;code class=&quot;changelog-code&quot;&gt;*_warning_level&lt;/code&gt; fields were removed from the domain verification response.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The API reference now describes the DMARC, SPF and DKIM fields the response already returned. DKIM, DMARC and SPF status stay &lt;code class=&quot;changelog-code&quot;&gt;null&lt;/code&gt; until a domain has been verified at least once, and &lt;code class=&quot;changelog-code&quot;&gt;cname_status&lt;/code&gt; is &lt;code class=&quot;changelog-code&quot;&gt;not_applicable&lt;/code&gt; for a sending domain at the root of your domain, which uses SPF instead of a CNAME record. Check any code that reads the removed fields.&lt;/p&gt;&lt;h3&gt;Deferred Loading For Dashboard And Audience Panels&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The dashboard and the Audience pages now open straight away and show placeholders while their slower panels load.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The three domain health panels on the dashboard now load together instead of separately. When a filter changes, the Audience table stays on screen, dimmed, until the new results arrive, so the page doesn't jump and selected rows stay selected.&lt;/p&gt;&lt;h3&gt;App Typefaces, Colors And Corners Updated To The Lettr Brand&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The app now uses the Lettr brand's typefaces and pink, square corners throughout, and an off-white background in light mode with near-black in dark mode.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Page content now sits in a centred column, so tables no longer stretch across the full width of a very large monitor.&lt;/p&gt;&lt;h2&gt;Bugfixes&lt;/h2&gt;&lt;ul&gt;&lt;li&gt;Fixed the daily sending counter showing the previous day's count after midnight UTC, which could leave a free team's daily limit stuck.&lt;/li&gt;&lt;li&gt;The app navigation can now be opened on screens narrower than 768px, where there used to be no button to open it.&lt;/li&gt;&lt;li&gt;Adding an email address that is already in your audience no longer returns a server error, and the result says how many already existed.&lt;/li&gt;&lt;li&gt;The Add contacts dialog now confirms that the contacts were added and returns you to the page you added them from.&lt;/li&gt;&lt;li&gt;Contacts added from inside a list now go into that list instead of All Contacts.&lt;/li&gt;&lt;li&gt;Fixed the “your export is ready” email with the download link never arriving after a contact export.&lt;/li&gt;&lt;li&gt;Audience times now show in your own timezone instead of about two hours off, though entries saved before this fix keep the old time.&lt;/li&gt;&lt;li&gt;Fixed a caching gap that could serve our asset files with the cross-origin permission meant for a different website.&lt;/li&gt;&lt;li&gt;When sign-up rejects a password, email or name, the form now returns to the step with the problem instead of hiding the error.&lt;/li&gt;&lt;li&gt;Toggle switches across the app now show whether they are on or off correctly.&lt;/li&gt;&lt;li&gt;Double-clicking the create button in the segment dialog no longer creates the same segment twice.&lt;/li&gt;&lt;li&gt;Fixed Audience layout faults: pagination hidden under the chat button, filters disappearing when nothing matched, pages shifting between tabs, and swapped Import and Export icons.&lt;/li&gt;&lt;li&gt;Campaign activity now loads a full page of recipients every time, where it used to show one of dozens and need “Load more” twice.&lt;/li&gt;&lt;li&gt;The event tabs in campaign activity and the stat counters now name each type of event the same way, so their numbers match.&lt;/li&gt;&lt;/ul&gt;</content>
  </entry>
  <entry>
    <id>https://lettr.com/changelog/2026-03/</id>
    <title>Lettr changelog: March 2026</title>
    <link rel="alternate" type="text/html" href="https://lettr.com/changelog/2026-03/"/>
    <published>2026-03-10T00:00:00Z</published>
    <updated>2026-03-10T00:00:00Z</updated>
    <summary>Everything Lettr shipped in March 2026: 2 new features, 9 improvements and 8 bugfixes, including Audience Module With Contacts, Lists, Segments And Topics.</summary>
    <content type="html">&lt;h2&gt;New features&lt;/h2&gt;&lt;h3&gt;Audience Module With Contacts, Lists, Segments And Topics&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The new Audience section keeps the people you send to as contacts and groups them into lists, segments and topics.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A contact is an email address with a status and any number of properties your team defines. Each property has a type and can have a fallback value, so a merge tag still shows something for a contact who never filled the field in. Lists are groups filled by hand, by import or through the API. Topics record what each contact agreed to receive, so unsubscribing from one topic keeps the others.&lt;/p&gt;&lt;p&gt;A segment stores conditions instead of members and is checked every time it is used, so it matches different contacts as the audience changes. It offers sixteen operators, limited to the ones that fit each property type, can be limited to one list, and shows the matching contacts while the conditions are being written. A segment can also be described in a sentence, which is turned into conditions you can edit.&lt;/p&gt;&lt;p&gt;A CSV import has three steps: upload, column mapping, and an import that runs in the background and emails you when it is done. Lettr detects whether the first row holds headers, adds headers when it doesn't, and suggests which column goes to which property. A contact that already exists is either skipped (the default) or updated with the row's properties, and contacts are matched by email address regardless of letter case, so an import never creates duplicates. Rows with a missing or invalid address are counted and reported instead of stopping the import. Contact exports arrive by email as a download link that works for 7 days.&lt;/p&gt;&lt;p&gt;The new &lt;code class=&quot;changelog-code&quot;&gt;audience:read&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;audience:write&lt;/code&gt; API key scopes allow listing, creating and deleting contacts and lists, and reading segments and their contacts. A contact created through the API can go through double opt-in: Lettr sends a confirmation email, using one of your emails named in the request, and a public confirmation link confirms the contact and redirects to an address you choose.&lt;/p&gt;&lt;h3&gt;API Failure Rate Alerts By Email And Webhook&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A new Alerts page in Settings tells the team owner when the share of failing API requests goes up.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Two checks run, one over the last 15 minutes for sudden failures and one over the last day for slower ones. When the failure rate crosses the alert threshold, the team owner is notified, at most once per cooldown period you set. A quiet account needs a minimum number of requests before it can be alerted, so one failed call is not enough, and the daily alert is skipped when the 15-minute one has already gone out.&lt;/p&gt;&lt;p&gt;Alerts arrive by email, by webhook, or both. A webhook address must be public, a test button sends a sample alert, and every delivery is signed with a secret for your team that can be regenerated.&lt;/p&gt;&lt;h2&gt;Improvements&lt;/h2&gt;&lt;h3&gt;Separate Contact-Based Billing Tier For Audience&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Audience is billed on its own, by the number of contacts you keep, separately from the plan for emails sent.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Adding an audience doesn't change what your current plan costs, and the first 500 contacts are free on every subscription. Moving to a smaller tier is refused while you have more contacts than it allows, instead of removing contacts to fit.&lt;/p&gt;&lt;h3&gt;Sending Domain Allow-List For API Keys&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;An API key can now be limited to a list of sending domains, and a send from any other domain is rejected with a &lt;code class=&quot;changelog-code&quot;&gt;domain_not_allowed&lt;/code&gt; error.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A key with no domains listed can send from any domain, so existing keys work as before. A leaked key that is limited this way can only send from the domains on its list.&lt;/p&gt;&lt;h3&gt;Custom Headers Field For The Send Email Endpoint&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;&lt;code class=&quot;changelog-code&quot;&gt;POST /api/emails&lt;/code&gt; now accepts a &lt;code class=&quot;changelog-code&quot;&gt;headers&lt;/code&gt; object with up to 10 custom headers, each value up to 998 characters.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Headers that decide where an email goes or how it is signed can't be set, including &lt;code class=&quot;changelog-code&quot;&gt;From&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;To&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;Reply-To&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;Subject&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;Date&lt;/code&gt;, &lt;code class=&quot;changelog-code&quot;&gt;Message-ID&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;DKIM-Signature&lt;/code&gt;. &lt;code class=&quot;changelog-code&quot;&gt;List-Unsubscribe&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;List-Unsubscribe-Post&lt;/code&gt; can't be set either, because Lettr adds them itself.&lt;/p&gt;&lt;h3&gt;Optional Subject Field For Sends With A Template&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A send with &lt;code class=&quot;changelog-code&quot;&gt;template_slug&lt;/code&gt; and no &lt;code class=&quot;changelog-code&quot;&gt;subject&lt;/code&gt; now uses the subject saved on that email, or the email's name when it has no subject.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;code class=&quot;changelog-code&quot;&gt;subject&lt;/code&gt; used to be required on every send. A &lt;code class=&quot;changelog-code&quot;&gt;subject&lt;/code&gt; in the request still takes priority over the saved one, &lt;code class=&quot;changelog-code&quot;&gt;GET /api/templates/html&lt;/code&gt; now returns the saved subject too, and the API reference no longer lists &lt;code class=&quot;changelog-code&quot;&gt;subject&lt;/code&gt; as required.&lt;/p&gt;&lt;h3&gt;AI Content Chat In The HTML Email Editor&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The HTML email editor now has an AI chat that changes the email from a description in plain language.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Each change is saved as a new version of the email, so the previous version is still there.&lt;/p&gt;&lt;h3&gt;Quick-Create Menu In The Top Bar And Refreshed App Design&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A “+” menu in the top bar now creates a sending domain, an API key, an email or a teammate invitation from any page.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The sign-in and registration pages were redesigned at the same time, the team switcher was rebuilt, and buttons, cards, inputs, tabs and dialogs got a refreshed look. The Lettr logo, in light and dark versions, replaced the text label.&lt;/p&gt;&lt;h3&gt;Password Confirmation For Account Email Changes&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Changing the email address on your account now requires your current password, while changing only your name does not.&lt;/strong&gt;&lt;/p&gt;&lt;h3&gt;Dark Mode In The Topol Editor&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The Topol editor in Lettr now has a dark mode.&lt;/strong&gt;&lt;/p&gt;&lt;h3&gt;Templates HTML And Projects Endpoints Added To The API Reference&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The API reference now documents &lt;code class=&quot;changelog-code&quot;&gt;GET /templates/html&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;GET /projects&lt;/code&gt;, and no longer lists an old request format that no endpoint used.&lt;/strong&gt;&lt;/p&gt;&lt;h2&gt;Bugfixes&lt;/h2&gt;&lt;ul&gt;&lt;li&gt;&lt;code class=&quot;changelog-code&quot;&gt;reply_to&lt;/code&gt; sent as an array or an object is now accepted, where it used to fail with “must be a valid email address”. A one-item array is unwrapped, and an object's &lt;code class=&quot;changelog-code&quot;&gt;email&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;name&lt;/code&gt; become &lt;code class=&quot;changelog-code&quot;&gt;reply_to&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;reply_to_name&lt;/code&gt;.&lt;/li&gt;&lt;li&gt;Fixed emails with attachments sent over SMTP bouncing instead of being delivered.&lt;/li&gt;&lt;li&gt;Sign-in, registration and password reset forms now work when the CAPTCHA is slow to load or times out, instead of failing.&lt;/li&gt;&lt;li&gt;The password reset form no longer reveals whether an email address has a Lettr account, because both outcomes now show the same message.&lt;/li&gt;&lt;li&gt;Fixed a tab left open during a Lettr update breaking on the next click; the page now reloads onto the new version.&lt;/li&gt;&lt;li&gt;The sign-in and registration pages are now served with their security response headers, which they used to be missing.&lt;/li&gt;&lt;li&gt;The description line under the headings on the sign-in and registration screens is shown again.&lt;/li&gt;&lt;li&gt;Fixed a mistake in the Laravel code example on the onboarding screen.&lt;/li&gt;&lt;/ul&gt;</content>
  </entry>
  <entry>
    <id>https://lettr.com/changelog/2026-02/</id>
    <title>Lettr changelog: February 2026</title>
    <link rel="alternate" type="text/html" href="https://lettr.com/changelog/2026-02/"/>
    <published>2026-02-14T00:00:00Z</published>
    <updated>2026-02-14T00:00:00Z</updated>
    <summary>Everything Lettr shipped in February 2026: 3 new features, 12 improvements and 3 bugfixes, including Public Launch Of The Lettr Email API and Sandbox API Keys.</summary>
    <content type="html">&lt;h2&gt;New features&lt;/h2&gt;&lt;h3&gt;Public Launch Of The Lettr Email API&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Lettr is now open to everyone: an email API built for Laravel, from the team behind Topol.io and DMARCeye.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Installing the &lt;code class=&quot;changelog-code&quot;&gt;lettr/lettr-laravel&lt;/code&gt; package and adding an API key is all it takes to send the first email. Applications that already send over SMTP can use the SMTP relay instead of the REST API, and an MCP server lets an AI assistant work with your emails and analytics.&lt;/p&gt;&lt;p&gt;Emails are built in the drag-and-drop Topol editor or written as HTML. Merge tags fill them in for each recipient, and a saved section used in several emails is updated in all of them when it is edited. The images in your emails can be served from your own domain.&lt;/p&gt;&lt;p&gt;Adding a sending domain shows its DNS records next to the name of your DNS provider, which Lettr finds from the domain's nameservers, and for Cloudflare it creates a one-click setup link. Records are checked again after the domain is verified, and a record is only marked broken after a short grace period and several failed checks in a row, so one slow lookup doesn't undo a verified domain.&lt;/p&gt;&lt;p&gt;The dashboard shows delivery and open rates with trends. A &lt;code class=&quot;changelog-code&quot;&gt;tag&lt;/code&gt; on a send groups the analytics by kind of email, such as password resets or invoices, and is filled in from the email's slug when it is not set. The event log shows what happened to each message, and alerts warn when you are close to your plan limit or a domain is unverified or blocked.&lt;/p&gt;&lt;p&gt;API keys can be limited to a set of IP addresses, and every send returns your remaining quota in its response headers. Requests are limited to 3 per second across all of a team's keys. The free plan needs no card and includes 3,000 emails a month, with at most 100 a day; paid plans start at 50,000 a month.&lt;/p&gt;&lt;h3&gt;Sandbox API Keys&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;An API key can now be created as Sandbox instead of Live, and a sandbox key works without a verified sending domain.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A sandbox send costs nothing and reaches only you: every recipient is replaced with your own address, &lt;code class=&quot;changelog-code&quot;&gt;cc&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;bcc&lt;/code&gt; are left out, and the send doesn't count against your quota or daily limit. Sandbox keys have their own rate limit of 10 requests a minute and 100 a day, and every endpoint that changes your account refuses them with a 403, so a sandbox key can't change anything.&lt;/p&gt;&lt;p&gt;Sandbox sends can be read back through the same endpoints as other emails, and a new Sandbox switch on the Events page shows them in the app.&lt;/p&gt;&lt;h3&gt;Scheduled Sending Endpoints With A Three-Day Window&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;New endpoints under &lt;code class=&quot;changelog-code&quot;&gt;/emails/scheduled&lt;/code&gt; schedule a send for later, look it up, and cancel it before it goes out.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;code class=&quot;changelog-code&quot;&gt;scheduled_at&lt;/code&gt; must be at least five minutes and at most three days ahead. A scheduled send goes through the same checks as an immediate one, so domain checks, quota and counters all apply in the same way.&lt;/p&gt;&lt;h2&gt;Improvements&lt;/h2&gt;&lt;h3&gt;API Key Scopes Enforced On Every Endpoint&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;API key permissions are now checked on every API endpoint, where they used to have no effect.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Ten scopes cover sending, templates, domains, webhooks and projects. The full preset grants all of them, the sending-only preset grants only the send scopes, and a custom list of scopes is accepted too. A request the key has no permission for returns a 403 with &lt;code class=&quot;changelog-code&quot;&gt;insufficient_scope&lt;/code&gt;.&lt;/p&gt;&lt;p&gt;A sending-only key used to read templates or domains no longer can, so give any key that needs those reads full access or the matching scopes.&lt;/p&gt;&lt;h3&gt;Create, Update And Delete Endpoints For Webhooks&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Webhooks can now be created, updated and deleted through the API, not only in the app.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;An update changes only the fields it sends: the name, the target URL, the auth type, the subscribed events or whether the webhook is active.&lt;/p&gt;&lt;h3&gt;Account-Wide Events Endpoint With Typed Event Objects&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The new &lt;code class=&quot;changelog-code&quot;&gt;GET /emails/events&lt;/code&gt; searches events across all of your emails instead of one message at a time, filtered by event type, recipient, date range and bounce class.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Each of the 18 event types, such as delivery, bounce, delay, click, open, spam complaint, unsubscribe and policy rejection, now returns its own fields. Events also include the browser, operating system and device read from the user agent, and location data. Opens that a mailbox provider loaded in advance are labelled as prefetched in the event log. The email list and detail responses now include &lt;code class=&quot;changelog-code&quot;&gt;from&lt;/code&gt; and &lt;code class=&quot;changelog-code&quot;&gt;to&lt;/code&gt;.&lt;/p&gt;&lt;h3&gt;Substitution Data Accepts Arrays Of Objects For Loops&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;&lt;code class=&quot;changelog-code&quot;&gt;data&lt;/code&gt; on a send now accepts numbers, true/false values and arrays of objects, where it used to accept only a flat map of strings.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Order lines, itemised receipts and digest lists can now be looped over inside the email instead of being turned into one string before sending. Objects nested more than one level deep are rejected, and the error names the key that caused it.&lt;/p&gt;&lt;h3&gt;Saving An Email Creates A New Version Instead Of A Draft&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Saving an email now creates a new version, and the separate draft is gone.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The draft used to need a publish step, with a draft badge and a next-version indicator; all three have been removed. Merge tags are saved with each version, the update response names the version it created, and the editor can open any earlier version.&lt;/p&gt;&lt;h3&gt;Sending Domains Usable Without Manual Approval&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A new sending domain can now send straight away, where it used to stay pending until someone reviewed and approved it.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Problem domains are now blocked at send time instead. A send from a blocked domain fails with an error that says so, where it used to be accepted without one.&lt;/p&gt;&lt;h3&gt;Templates Renamed To Emails In The App&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;What the app called templates is now called emails everywhere, and the API stays the same.&lt;/strong&gt;&lt;/p&gt;&lt;h3&gt;Required Flag For Merge Tags Per Email Version&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A merge tag on an email version can now be marked required by clicking its badge, and required tags are highlighted.&lt;/strong&gt;&lt;/p&gt;&lt;h3&gt;Redesigned Version History That Keeps The Last Version&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Version history has a new layout with clearer wording on what saving and publishing each do, and the last remaining version can no longer be deleted.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Previewing a version that isn't the live one is now marked in grey instead of a warning color, since looking at an old version is a normal thing to do.&lt;/p&gt;&lt;h3&gt;Expired Google And GitHub Sign-Ins Return To The Login Page&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;A Google or GitHub sign-in that expired because the tab was left open now returns to the login page with a message to try again, instead of an error.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A very long avatar URL from the provider can also no longer stop the account from being created.&lt;/p&gt;&lt;h3&gt;Password Changes Sign Out All Other Sessions&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;Changing your password now signs you out of Lettr on every other device and browser.&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;User and team names are also stripped of markup when saved, so a name can't carry code into an email or a page.&lt;/p&gt;&lt;h3&gt;API Reference Updated For Email Detail And All Event Types&lt;/h3&gt;&lt;p&gt;&lt;strong&gt;The API reference no longer lists paths and schemas that were removed, documents the email detail endpoint properly, and describes every event type.&lt;/strong&gt;&lt;/p&gt;&lt;h2&gt;Bugfixes&lt;/h2&gt;&lt;ul&gt;&lt;li&gt;The quickstart email is no longer sent again each time an already verified account receives another verification event.&lt;/li&gt;&lt;li&gt;Fixed the single-email endpoint returning an unrelated error code when a message couldn't be retrieved; it now returns its own code.&lt;/li&gt;&lt;li&gt;Event latitude and longitude are now always strings, where whole numbers used to come back as numbers.&lt;/li&gt;&lt;/ul&gt;</content>
  </entry>
</feed>
