Split out of the combined D1.2 mail-adoption issue (community-base plan phase 1).
Scope:
- P2: install
community_base.mail (v0.3.0) - URL include at the site root after email_app (package callback ingress goes live; recipient links stay with email_app until D1.2c), studio include under /studio/mail/, MAIL_TEMPLATE_DIR pointing at email_templates/.
- P6: copy
email_app.PendingUnsubscribe into cb_mail.PendingUnsubscribe with a copy_forward/copy_backward data migration (batch 1000, donor model kept).
- Commit the five DTC purpose templates in
email_templates/ (deadline reminder, course registration confirmation, enrollment confirmation, certificate ready, Slack access) as the source of truth mirrored into Relay by the deploy's import_mail_templates step.
- Relay import + publish version 1: not run here; needs a permitted development Relay with the R1.5 tag (deploy step and template tests land first).
Verification: manage.py check, makemigrations --check, fresh-database migrations, template render tests per purpose, mirror-command tests against FakeRelay. Development-copy row counts deferred until a development copy exists locally.
Split out of the combined D1.2 mail-adoption issue (community-base plan phase 1).
Scope:
community_base.mail(v0.3.0) - URL include at the site root afteremail_app(package callback ingress goes live; recipient links stay withemail_appuntil D1.2c), studio include under/studio/mail/,MAIL_TEMPLATE_DIRpointing atemail_templates/.email_app.PendingUnsubscribeintocb_mail.PendingUnsubscribewith a copy_forward/copy_backward data migration (batch 1000, donor model kept).email_templates/(deadline reminder, course registration confirmation, enrollment confirmation, certificate ready, Slack access) as the source of truth mirrored into Relay by the deploy'simport_mail_templatesstep.Verification: manage.py check, makemigrations --check, fresh-database migrations, template render tests per purpose, mirror-command tests against FakeRelay. Development-copy row counts deferred until a development copy exists locally.