Skip to content

Show the critical-alert notice on the signup form - #1010

Draft
RisingOrange wants to merge 7 commits into
mainfrom
feat/critical-alert-signup-notice
Draft

Show the critical-alert notice on the signup form#1010
RisingOrange wants to merge 7 commits into
mainfrom
feat/critical-alert-signup-notice

Conversation

@RisingOrange

@RisingOrange RisingOrange commented Jul 29, 2026

Copy link
Copy Markdown
Collaborator

Shows the critical-alert notice on the signup form. It was written into the form but commented out, so no signup has ever seen it. Maxime asked for it to be shown.

Why the checkbox doesn't already cover it

The case is someone who ticks only the required privacy-policy box and neither optional box. They are still added to the critical alerts list in CiviCRM, but nothing in the form tells them any email may follow. The required box covers the privacy policy and chapter sharing, and the policy's only email disclosures are the opt-in Substack newsletter and "contact you via Airtable" for coordination.

Wording

We may occasionally send you a critical alert, even if you don't opt into any of these. See our [privacy policy].

The critical-alert notice under the two opt-in checkboxes on the intent step

"any of these" points at the two checkboxes above it. "critical" and "occasionally" keep this a bounded tier rather than "we may email you anything", which would undercut the opt-in it bypasses. "critical alert" matches the unsubscribe page name (PauseAI Critical Alerts) — in English, at least; that page is English-only.

Implementation

  • Step 2, under the two opt-in checkboxes, not the email field where the commented-out draft sat: step 1 shows no opt-ins for the clause to point at, and submits nothing (onsubmit={continueToIntent}), so no data leaves the browser before step 2.
  • Not on the browse mini-form, which hardcodes keep_informed=on — submitting it is the opt-in, so the clause would be false there. Its required privacy-policy checkbox still carries the general disclosure.
  • aria-describedby on both controls, so the notice is not a paragraph a screen-reader user tabs straight past. First use in this file: the other helper texts are hints, this one is a disclosure.
  • onboarding_email_critical_notice in messages.ts (en/de/fr) rather than inline English, following onboarding_gdpr_consent, which also carries the privacy link as inline markup via {@html}.

Checks

CI green: pnpm-check, CodeQL, and a Netlify deploy preview worth clicking through to see it on a real build.

The de and fr wording is mine and wants a native-speaker read — four defects surfaced in it during review, which no check here would have caught.

Context: PauseAI/pauseai-civicrm#389 and PauseAI/pauseai-civicrm#344.

The notice has been in the form but commented out since it was written, so
no signup has ever seen it. Maxime asked for it to be shown.

It matters for one specific group: someone who ticks only the required
privacy-policy box and neither optional box. They are still added to the
critical alerts list in CiviCRM, so they can be reached if something
urgent happens, but nothing in the form tells them any email may follow.
The required checkbox covers the privacy policy and chapter sharing, and
the privacy policy itself only describes the opt-in Substack newsletter
and contact via Airtable for coordination. That population is 64 people
today and grows by roughly 60 a month.

Reworded from "We may contact you about critical mobilizations": we do not
use the word "mobilization" anywhere a signup would see, and "critical
alert" matches the name on the unsubscribe page (PauseAI Critical Alerts),
so the wording at signup and at unsubscribe agree. "critical" and
"occasionally" are load-bearing, keeping this a bounded tier rather than
"we may email you anything", which would undercut the opt-in it bypasses.

Moved into messages.ts as onboarding_email_critical_notice rather than
left as inline English, with de and fr, following onboarding_gdpr_consent
which likewise carries the privacy link as inline markup rendered through
{@html}. Both form variants use the same key.
@netlify

netlify Bot commented Jul 29, 2026

Copy link
Copy Markdown

Deploy Preview for pauseai ready!

Name Link
🔨 Latest commit a11b56f
🔍 Latest deploy log https://app.netlify.com/projects/pauseai/deploys/6a6b7dab9828a40008e91b0f
😎 Deploy Preview https://deploy-preview-1010--pauseai.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.
Lighthouse
Lighthouse
1 paths audited
Performance: 52 (🔴 down 3 from production)
Accessibility: 91 (no change from production)
Best Practices: 100 (no change from production)
SEO: 82 (no change from production)
PWA: -
View the detailed breakdown and full score reports
🤖 Make changes Run an agent on this branch

To edit notification comments on pull requests, go to your Netlify project configuration.

The German read "Wir senden dir gelegentlich eine kritische Warnung",
which is declarative: we DO send these. The English and French both
reserve the right rather than promise the act ("We may", "Nous pouvons").
In a notice whose whole purpose is telling someone what we might do with
their address, that is the wrong claim. Now "Wir können ... senden".
Two problems with putting it under the email field on step 1.

The sentence says "even if you don't opt into anything else", but step 1
shows no opt-ins at all: the two checkboxes are on step 2. The clause
pointed at something the reader had not seen yet. Moving it under those
checkboxes gives it a referent, and costs nothing in notice-at-collection
terms, because step 1 submits nothing: its form is onsubmit=continueToIntent,
which only advances the step. Data first leaves the browser when step 2 posts.

"else" also presupposed a first thing the reader had opted into, which
quietly framed critical alerts as one more option on the form, when the
point is that they are the one thing you do not choose. Now "any of these",
which points at the checkboxes above it. Reworded in all three locales.

Also drops the notice from the browse mini-form. That form hardcodes
keep_informed=on, so submitting it IS the opt-in, and telling those users
we may write "even if you don't opt into any of these" is simply false.
The required privacy-policy checkbox still carries the general disclosure
there.
"kritische Warnung" read as a translation: "Warnung" already is an alert,
so the qualifier is close to redundant, and "kritisch" in German leans
toward "critical of" or "in a critical condition" rather than "important".

Now "In dringenden Fällen könnten wir dir eine Nachricht senden". Nothing
is lost by dropping "kritisch": the reason English says "critical alert" is
to match the unsubscribe page (PauseAI Critical Alerts), and that page is
English-only, so the German is free to be idiomatic.

Note this bounds the promise differently from the English. English bounds by
frequency ("occasionally"), the German by circumstance ("in dringenden
Fällen"), which is the harder bound to stretch. Singular "eine Nachricht"
carries the rarity that "occasionally" carries in English; the plural read
like an ongoing stream, which is what this tier is trying not to be.

Stays informal: the German locale is 56 du/dich/dir forms and no Sie, so a
formal sentence here would be the only one on the form.
The string was the only vouvoiement in the French locale: 39 tu forms
against 2 vous, both of them mine. It now uses tu like everything else.

Three other things went with it. "Voir notre..." was an infinitive label,
where the locale uses tu-imperatives for links ("Consulte notre liste
d'actions"), so it is now "Consulte notre". "n'en sélectionnes aucune" left
the pronoun without a named antecedent, which English gets away with because
"these" points at the checkboxes on screen; French now says "aucune de ces
options". And "alerte critique" carried the same redundancy "kritische
Warnung" did in German, since "alerte" already conveys urgency, so it is
now "alerte urgente".

Unlike the German, this keeps the English's two bounds: occasion ("urgente")
and frequency ("occasionnellement").
"nichts davon auswählst" left the reference dangling: "davon" points back
at something the sentence never names. Same weakness the French had with
"n'en sélectionnes aucune", fixed there in the previous commit.

Now "keine dieser Optionen wählst". The demonstrative does the work "these"
does in English and "ces options" in French, pointing at the two checkboxes
the notice sits directly beneath.
A review pointed out the notice was a standalone paragraph after the two
checkbox-style buttons, with nothing tying them together. A screen-reader
user tabbing through the controls hears both buttons and then the first
radio option, and can pass the notice without ever meeting it. For a
paragraph whose whole purpose is to be read before you decide not to tick
anything, that defeats the point of showing it at all.

Both controls now carry aria-describedby pointing at the paragraph's id.
Nothing else in this file uses aria-describedby, so this is the first
instance rather than a convention being followed; the other helper texts
are hints, whereas this one is a disclosure.

The eslint-disable moved inside the <p>: Prettier splits the element across
lines once it has two attributes, which left the disable applying to the
opening tag rather than the {@html} it was written for, and the rule fired.
@RisingOrange
RisingOrange marked this pull request as ready for review July 30, 2026 16:46
@RisingOrange
RisingOrange requested a review from hturnbull93 July 30, 2026 16:46
@RisingOrange RisingOrange changed the title feat(onboarding): show the critical-alert notice on the email field Show the critical-alert notice on the signup form Jul 30, 2026

@hturnbull93 hturnbull93 left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Lgtm, though best to show Maxime and Irina to make sure this is ok GDPR wise. I think there's a chance we may need to put it by the submit button as a mandatory checkbox, as we might not be able to have the submit itself assume consent.

RisingOrange added a commit that referenced this pull request Aug 1, 2026
Reuse the shipping notice string from PR #1010 ('...even if you don't opt into
any of these...') instead of a bespoke variant, so the prototype and the
in-flight notice read the same. The wording fits V2 even better than the current
form, since V2 drops the tick-at-least-one rule that made 'opt into nothing'
impossible.
@RisingOrange
RisingOrange marked this pull request as draft August 3, 2026 22:10
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants