- send_test no longer overwrites {{ UnsubscribeURL }} with a dead static URL;
Listmonk renders it into a working per-subscriber unsubscribe link.
- dot-compliance hero grid: 4 columns (minmax 150px, max-width 920px) instead
of 3 to reduce vertical space.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
- import_subscribers: was POSTing wrong bulk shape AND fallback used 'list_ids'
(ignored by Listmonk) instead of 'lists' -> subscribers never attached to the
list -> real sends would go to an empty list. Now single-adds with 'lists',
handles already-exists, returns a count, logs if 0 added.
- send_test: passed base['lists'] (objects) instead of IDs -> test send rejected.
Now extracts list IDs.
- create_and_schedule_campaign: add schedule= flag (preview makes drafts).
- --preview: 1 sample carrier/campaign, only owner email, drafts not scheduled,
test sends immediately, never marks real carriers sent.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Each of the 8 daily campaigns gets a test send immediately after creation
using the first row's real carrier data as the sample. TEST_EMAIL env var
overrides the default (carrierone@gmx.com).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- build_trucking_campaigns.py: nightly script that creates 8 Listmonk campaigns
per day (4 TZ x 2 types: MCS-150 overdue 2k/TZ, inactive USDOT 1k/TZ)
at 4AM ET / 5AM ET (CT) / 6AM ET (MT) / 7AM ET (PT). Deduplicates via
listmonk_sent_at column.
- migration 083: add listmonk_sent_at + listmonk_campaign_type to fmcsa_carriers
- email_verifier.py: bump max_workers from 5 to 20 for 4x faster throughput
- cron: daily pw-trucking-campaigns at 08:00 UTC (3 AM EST)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>