Skip to content

fix(mailer): drop hand-built appName/appContact, brand the subjects - #4177

Merged
PierreBrisorgueil merged 2 commits into
masterfrom
feat/4131-drop-appname-appcontact
Oct 3, 2026
Merged

PierreBrisorgueil merged 2 commits into
masterfrom
feat/4131-drop-appname-appcontact

Conversation

@PierreBrisorgueil

@PierreBrisorgueil PierreBrisorgueil commented Oct 3, 2026 •

Copy link
Copy Markdown
Contributor

Summary

  • What changed: Removed the hand-built appName/appContact params at the 14 sendMail call sites across auth, billing, invitations, organizations, and users — the mailer's render() already injects both from getBrand(). Switched the 8 subjects that embedded the app title to getBrand().name (5 in billing.email.js, 1 each in billing.referral.service.js, invitations.service.js, organizations.service.js). Subjects built from org.name, and the 4 fixed English subjects, are unchanged.
  • Why: getBrand() (from ✨ Mailer: central brand values via config.mailer.brand #4130) is now the single source of truth for brand values with a config.app.title/config.app.contact fallback baked in, so passing appName/appContact by hand at every call site was redundant and a drift risk the moment a downstream sets config.mailer.brand.
  • Related issues: Closes 🔧 Mail call sites: drop hand-built appName/appContact, brand the subjects #4131

Scope

  • Module(s) impacted: auth, billing, invitations, organizations, users
  • Cross-module impact: none (all call sites consume the same lib/helpers/mailer getBrand()/render() seam already in place)
  • Risk level: low (deletion-only at 13 of 14 call sites; the 14th and the 5 billing subjects move from reading config.app?.title to mailer.getBrand().name, which falls back to the same config.app.title when no brand config is set)

Validation

  • npm run lint — clean
  • npm test — 2770/2770 unit tests pass (coverage gate passes); integration/E2E run in CI (local MongoDB infra was down for this pass)
  • Manual checks done (if applicable) — all 15 mailer template snapshots pass unchanged, confirming byte-identical rendered bodies/subjects with no brand config set

Guardrails check

  • No secrets or credentials introduced (.env*, secrets/**, keys, tokens)
  • No risky rename/move of core stack paths
  • Changes remain merge-friendly for downstream projects
  • Tests added or updated when behavior changed (7 test files updated: billing.init.email-alerts, billing.referral.service, invitations.service, organizations.emailVerification(.policy), organizations.membership.addMember.email, organizations.service.signup, organizations.service.welcomeEmail)

Notes for reviewers

Summary by CodeRabbit

  • Updates
    • Email subjects for billing, referral, invitation, and organization welcome messages now use the mailer’s configured brand name.
    • Email templates no longer receive app name or contact details as parameters. Existing display names, links, and other message details remain unchanged.

render() already injects appName/appContact from the resolved brand
(#4164-#4171), so the hand-built params at the 14 sendMail call sites
are redundant. Drop them, and switch the 8 subjects that embedded the
app title to mailer.getBrand().name so a mailer.brand.name override
reaches the subject too. Subjects built from org.name and the 4 fixed
English subjects are unchanged. With no brand config, brand.name falls
back to config.app.title, so output is byte-identical.

Refs #4131
mockMailer.getBrand.mockReturnValue(...) persisted for every subsequent
call within the test instead of just the one assertion; mockReturnValueOnce
keeps the override scoped. Kimi review nit from Phase 0.
@PierreBrisorgueil PierreBrisorgueil added the Fix A bug fix label Oct 3, 2026
@PierreBrisorgueil PierreBrisorgueil self-assigned this Oct 3, 2026
@coderabbitai

coderabbitai Bot commented Oct 3, 2026 •

Copy link
Copy Markdown

Review in Change Stack →

Navigate logical layers of code changes, visualize relationships, and explore their blast radius.

🧰 Additional context used
📚 Code guidelines (1)
.github/copilot-instructions.md — auto-discovered

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration
  • Configuration used: Repository: pierreb-devkit/Node/.coderabbit.yaml
  • Review profile: ASSERTIVE
  • Plan: Advanced
  • Run ID: 4d365d29-2d53-4011-be71-0b37c43f9118
📥 Commits

Reviewing files that changed from the base of the PR and between e896520 and 514cea6.

📒 Files selected for processing (16)
  • modules/auth/controllers/auth.password.controller.js
  • modules/auth/services/auth.signup.service.js
  • modules/billing/billing.email.js
  • modules/billing/services/billing.referral.service.js
  • modules/billing/tests/billing.init.email-alerts.unit.tests.js
  • modules/billing/tests/billing.referral.service.unit.tests.js
  • modules/invitations/services/invitations.service.js
  • modules/invitations/tests/invitations.service.unit.tests.js
  • modules/organizations/services/organizations.membership.service.js
  • modules/organizations/services/organizations.service.js
  • modules/organizations/tests/organizations.emailVerification.policy.unit.tests.js
  • modules/organizations/tests/organizations.emailVerification.unit.tests.js
  • modules/organizations/tests/organizations.membership.addMember.email.unit.tests.js
  • modules/organizations/tests/organizations.service.signup.unit.tests.js
  • modules/organizations/tests/organizations.service.welcomeEmail.unit.tests.js
  • modules/users/services/users.service.js
💤 Files with no reviewable changes (5)
  • modules/users/services/users.service.js
  • modules/auth/services/auth.signup.service.js
  • modules/auth/controllers/auth.password.controller.js
  • modules/organizations/tests/organizations.membership.addMember.email.unit.tests.js
  • modules/organizations/services/organizations.membership.service.js

Included review availability: This review used your included allowance. Your plan provides up to 1 included review per hour; 0 remain after this review.


Walkthrough

Email call sites remove manually supplied app-name and contact parameters. Billing, invitation, and organization email subjects now use the mailer brand name in place of the configured app title.

Changes

Email branding and parameters

Layer / File(s) Summary
Authentication and membership email parameters
modules/auth/controllers/auth.password.controller.js, modules/auth/services/auth.signup.service.js, modules/users/services/users.service.js, modules/organizations/services/organizations.membership.service.js, modules/organizations/tests/organizations.membership.addMember.email.unit.tests.js
Password, signup, email-change, and organization membership emails no longer pass the removed app-name or contact parameters. The membership email test expectation is updated.
Billing email branding
modules/billing/billing.email.js, modules/billing/services/billing.referral.service.js, modules/billing/tests/billing.init.email-alerts.unit.tests.js, modules/billing/tests/billing.referral.service.unit.tests.js
Billing alert and referral subjects use the mailer brand name. Billing template parameters no longer include app-name or contact values. Tests add brand mocks and cover a brand-name override.
Invitation and organization email branding
modules/invitations/services/invitations.service.js, modules/invitations/tests/invitations.service.unit.tests.js, modules/organizations/services/organizations.service.js, modules/organizations/tests/organizations.emailVerification.*.unit.tests.js, modules/organizations/tests/organizations.service.signup.unit.tests.js, modules/organizations/tests/organizations.service.welcomeEmail.unit.tests.js
Invitation and welcome subjects use the mailer brand name. Their email parameters no longer include app-name or contact values. Related test mocks and expectations are updated.

Priority: ➖ Normal

Estimated code review effort: 2 (Simple) | ~12 minutes

Change: Bug fix

Merge Risk: ⚪ Minimal · up to 514ce

The branding changes have no established merge-blocking regression; the PR is ready for normal checks.

Security Architecture Review

Security architecture risk: 🔵 Low · up to 514ce

The inspected branding edits preserve email recipients, invitation-token links and legacy template parameters. No specific security regression is established, but uncertainty about the comparison baseline prevents an unqualified minimal-risk assessment.

Retained concerns
No architecture-level concerns identified.

Security review details

Security Blast Radius

  • inferred — The inspected branding change affects presentation in referral, invitation and welcome notifications. Those payloads retain their existing recipient sources; the evidence does not establish an expansion of recipient authority or invitation-token access.

Trust Boundaries and Controls

  • observed — Referral notifications obtain the destination from the identified user's stored email, while invitation messages use the invitation's email and token. Brand resolution supplies presentation values without selecting recipients or granting privileges.

Resilience and Maintainability Implications

  • observed — The inspected welcome-mail path runs after provisioning and contains synchronous and asynchronous delivery failures through logging. Sequential provisioning recovery can converge on an existing membership without another welcome send, so this path does not establish guaranteed notification delivery. That behavior is outside the supplied branding-only range and is not retained as a security regression.
🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly summarizes the main changes: removing hand-built app name and contact parameters and using the mailer brand for subjects.
Description check ✅ Passed The description includes the required Summary, Scope, Validation, Guardrails, and reviewer notes. It explains the changes, rationale, affected modules, risk, test results, and related issue.
Linked Issues check ✅ Passed #4131 requirements are addressed. The change removes hand-built appName/appContact parameters from the 14 listed mail call sites and switches the eight app-title subjects to mailer.getBrand().name. Su…
Out of Scope Changes check ✅ Passed The listed production changes are limited to the mail call sites and subject branding required by #4131. The test changes update mailer mocks and assert the requested behavior. No unrelated change app…
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check. Docstring coverage is scoped to functions touched by this diff. Analyzed 0 functions across 1…
✨ Finishing Touches
📝 Generate docstrings
  • Commit to this branch
  • Create a new PR
🧪 Generate unit tests (beta)
  • Commit to this branch
  • Create a new PR
  • Autopilot · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Warning

Some tools did not complete. Review the errors below.

🔧 ESLint

If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.

ESLint install failed: dependency version conflict. Check your lock file or package.json.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@PierreBrisorgueil
PierreBrisorgueil marked this pull request as ready for review October 3, 2026 22:37
@codecov

codecov Bot commented Oct 3, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 94.55%. Comparing base (e896520) to head (514cea6).

Additional details and impacted files
@@            Coverage Diff             @@
##           master    #4177      +/-   ##
==========================================
- Coverage   94.55%   94.55%   -0.01%     
==========================================
  Files         174      174              
  Lines        6137     6134       -3     
  Branches     1983     1979       -4     
==========================================
- Hits         5803     5800       -3     
  Misses        271      271              
  Partials       63       63              
Flag Coverage Δ
integration 64.05% <0.00%> (+0.03%) ⬆️
unit 79.85% <100.00%> (-0.01%) ⬇️

Flags with carried forward coverage won't be shown. Click here to find out more.


Continue to review full report in Codecov by Harness.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update e896520...514cea6. Read the comment docs.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@PierreBrisorgueil
PierreBrisorgueil merged commit da96fc1 into master Oct 3, 2026
8 checks passed
@PierreBrisorgueil
PierreBrisorgueil deleted the feat/4131-drop-appname-appcontact branch October 3, 2026 22:57
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Fix A bug fix

Projects

None yet

Development

Successfully merging this pull request may close these issues.

🔧 Mail call sites: drop hand-built appName/appContact, brand the subjects

1 participant