Skip to content

[finding] configure/notifications.mdx says a template's locale is "matched to the recipient" — the delivery path never reads a recipient locale #246

Description

@claude

Found while implementing #147, whose ruling covers the render object claim only (which channels read sys_notification_template). This is a separate claim about whose locale a template is matched on, so it was recorded rather than folded into that PR. Filed unassigned, observation class.

content/docs/configure/notifications.mdx tells an admin that a template's locale is the recipient's:

Measured on objectstack origin/main @ 9e0ba21, by tracing the delivery path:

  • messaging-service.ts contains no occurrence of locale at all. emit() builds each delivery from topic, title (payload.title falling back to the topic, :917/:949), body and payload; the recipient is a user id, and nothing resolves a locale for it.
  • email-channel.ts:224const locale = typeof payload.locale === 'string' ? payload.locale : defaultLocale; then store.load(n.topic, 'email', locale). defaultLocale is opts.defaultLocale ?? DEFAULT_LOCALE (:135), a channel-construction value.
  • sms-channel.ts:124 — the same two lines for (topic, 'sms', locale).
  • inbox-channel.ts:143-145 — the notify-template path takes payload.locale, else getDefaultTemplateLocale() (the deployment default).

So the locale a template is matched on is the notification's own — whatever the producer put in payload.locale, else a deployment-wide default. It is never looked up from the recipient, which means one notification renders in one locale for every recipient it fans out to. The upstream changeset says this in its own words for the template path: "one locale per notification: payload.locale, else the deployment default" (messaging-service-plugin.ts:250).

The practical consequence for an admin: authoring es and en rows for a topic does not give two recipients their own languages on one event; it gives whichever locale the producer named. That is the opposite of what "matched to the recipient" promises.

Not fixed under #147 because the honest replacement is a different claim from the one that card adjudicated, and its wording touches what the platform promises about localization — worth its own triage rather than a rider.

Related: #147 (render-object claim, corrected), objectstack packages/services/service-messaging.


Generated by Claude Code

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions