service-de-channel-consent-configure
Configure consent (opt-in/opt-out) on an Enhanced `MessagingChannel` so activation will accept it. Given a `{CHANNEL_ID}`, sets the channel's `ConsentType` (ImplicitOptIn / ExplicitOptIn / DoubleOptIn) and the `OptInPrompt` / `DoubleOptInPrompt` prompt fields, then creates or updates one `MsgChannel
By forcedotcom · 595 installs
npx skills add forcedotcom/sf-skills --skill service-de-channel-consent-configure
Source repository · Upstream listing
Configuring Channel Consent
What this skill does
Ensures an Enhanced MessagingChannel has valid consent configured before activation. Consent has two parts, and both are checked by the server side activation readiness gate ( MessagingChannelReadinessChecker.isConsentConfiguredForChannel ):
1. Channel level fields on MessagingChannel :
ConsentType — static enum: ImplicitOptIn , ExplicitOptIn , or DoubleOptIn .
OptInPrompt — message sent when an end user reply doesn't match an opt in keyword (required for ExplicitOptIn/DoubleOptIn, except on Unified SMS / WhatsApp / RCS where it's optional).
DoubleOptInPrompt — message sent when a reply doesn't match a double opt in keyword (required for DoubleOptIn).
IsRequireDoubleOptIn — boolean flag; set true alongside ConsentType=DoubleOptIn .
2. Per language keyword records — one or more MsgChannelLanguageKeyword child rows (master detail to MessagingChannel , key prefix 3Or ). Each holds the keywords an end user sends (opt in, double opt in, opt out, help, custom) and the confirmation replies, for one language . Keyword fields are comma separated strings (e.g. "STOP,UNSUBSCRIBE,CANCEL" ).
Consent is never a no op for activation. Even ImplicitOptIn requires at least one MsgChannelLanguageKeyword with an opt out keyword + opt out confirmation. (The one exception is an outbound only channel, which the readiness check passes automatically.)
Consent settings apply only to Enhanced channels ( PlatformType=Enhanced ) of a supported message type. On a Standard channel these fields aren't used; this skill only touches Enhanced channels.
Where this fits
This skill runs between routing and activation in the Enhanced channel setup pipeline. service de channel routing configure sets the channel's SessionHandler ; this skill configures consent; then service de channel activate flips the channel live. The activation readiness check requires both routing and consent, so run this before activating. The service de headless channel configure orchestrator sequences all three automatically — invoke this skill directly only when you want to configure consent on its own.
Reference File Index
Reference file Load when
references/language keywords.md Creating or updating the per language MsgChannelLanguageKeyword records — full field list, CSV keyword semantics, create vs update logic, and the Unified SMS help/custom keyword rules.
references/gotchas.md Troubleshooting an unexpected result, or before modifying this skill.
references/worked examples.md You want a reference run of the ImplicitOptIn, ExplicitOptIn, or DoubleOptIn paths.
When NOT to use this skill
The channel isn't Enhanced. Consent fields apply to Enhanced channels only. This skill confirms PlatformType=Enhanced and stops otherwise.
The channel is outbound only. Outbound only channels pass the consent readiness check automatically; there's nothing to configure.
The channel doesn't exist yet. Run the insertion skill first; this skill expects a real MessagingChannel.Id .
Inputs (from caller)
{CHANNEL ID} — a 15 or 18 char MessagingChannel.Id (prefix 0Mj ). Must already exist and be Enhanced.
{CONSENT TYPE} — optional; one of ImplicitOptIn ExplicitOptIn DoubleOptIn . If omitted, the skill prompts.
{LANGUAGE} — optional; the MasterLanguage for the keyword record (e.g. en US ). Defaults to en US if not provided.
{ORG ALIAS} — optional; sf CLI target org alias. Default: whatever sf config get target org returns.
The individual keyword/confirmation/prompt values are collected interactively in Stage 3–4 (or accepted from the caller if pre supplied).
Output (to caller)
Success — no change needed:
Success — consent configured:
Precondition / validation not met:
Failure:
Stage 1: Read current consent state
Read the channel's consent fields and any existing language keyword records.
If the channel record is missing — halt with Error: Channel {CHANNEL ID} not found — check the id, or run the insertion skill first.
If PlatformType != 'Enhanced' — emit {ok:false, kind:"not enhanced", ...} and stop.
No op check: if ConsentType is non null AND the existing language keyword records already satisfy the readiness matrix for that ConsentType (see Stage 5), emit the noop:true envelope and return. Don't re prompt or overwrite a channel that is already activation ready.
Stage 2: Choose the ConsentType
If {CONSENT TYPE} wasn't supplied, prompt (do NOT auto pick):
Record {CONSENT TYPE} . Note the field checks that follow (this is the exact server side activation readiness contract — see references/gotchas.md for the source):
ConsentType MessagingChannel fields MsgChannelLanguageKeyword (≥1 record)
ImplicitOptIn (none required) OptOutKeywords + OptOutConfirmation
ExplicitOptIn OptInPrompt ¹ above + OptInKeywords
DoubleOptIn OptInPrompt ¹ + DoubleOptInPrompt + IsRequireDoubleOptIn=true above + DoubleOptInKeywords
¹ OptInPrompt is optional (not required for readiness) on Unified SMS / WhatsApp / RCS channels — detect via MessageType IN ('Text','WhatsApp','Rcs') on an Enhanced channel (the queryable proxy for the server's isUnifiedSMSOrWhatsappOrRCS ). Still recommend setting it for a good end user experience.
Stage 3: Collect channel level prompt values
Only prompt for the fields the chosen ConsentType requires (see the matrix above). Skip this stage entirely for ImplicitOptIn — it needs no channel level prompt fields.
For ExplicitOptIn / DoubleOptIn :
For DoubleOptIn , also:
Trim whitespace. If a required prompt is empty after trimming, re prompt once; on a second empty, emit {ok:false, kind:"missing consent input", hint:"..."} .
Stage 4: Configure the per language keyword record
Collect the keyword lists and confirmation replies for {LANGUAGE} (default en US ), then create or update the MsgChannelLanguageKeyword record.
Load references/language keywords.md and follow it — it holds the full field list, the comma separated keyword semantics, the create vs update decision (reuse an existing record for the same language rather than duplicating), and the Unified SMS help/custom keyword rules.
The minimum per ConsentType (again, from the readiness contract):
ImplicitOptIn: OptOutKeywords (e.g. STOP,UNSUBSCRIBE ) + OptOutConfirmation .
ExplicitOptIn: the above + OptInKeywords (e.g. START,YES ).
DoubleOptIn: the above + DoubleOptInKeywords (e.g. CONFIRM ).
OptInConfirmation , HelpKeywords / HelpResponse , and CustomKeywords / CustomResponse are optional for the base readiness check (help/custom are only required on Unified SMS — see the reference), but collect them if the user wants them.
Stage 5: Write channel fields + keyword record
Write the channel level fields in one PATCH (only the fields the ConsentType requires).
Quoting rule (load bearing): sf data update record values splits on spaces, so any value containing a space must be wrapped in single quotes inside the double quoted values string — e.g. OptInPrompt='Reply YES to receive messages' . An unquoted OptInPrompt=Reply YES ... fails with Malformed key=value pair (verified live on sdb6c). Prompts almost always contain spaces, so always quote them.
If status !== 0 : emit {ok:false, kind:"channel patch failed", message: ...} and return.
Then create or update the MsgChannelLanguageKeyword record per references/language keywords.md . If it fails: {ok:false, kind:"keyword record failed", message: ...} .
Stage 6: Verify activation readiness
Re read both the channel and its keyword records (same two queries as Stage 1). Confirm, per the chosen ConsentType's row in the Stage 2 matrix, that every required field is now non null on the channel AND on at least one keyword record for the configured language.
If any required field is still null: emit {ok:false, kind:"verify failed", hint:"<which requirement is unmet "} .
Otherwise emit the success envelope with activationReady: true .
Stage 7: Report to caller
Report the JSON envelope. If this skill is the leaf (user invoked it directly), render:
Success — Consent configured — channel {CHANNEL ID} is now {CONSENT TYPE} with a {LANGUAGE} keyword record. Activation ready.
Info: Consent already configured — {CONSENT TYPE}, {N} language record(s). No changes. (no op path)
Warning: This channel is PlatformType={x}, not Enhanced — consent fields don't apply here. (not enhanced)
Warning: Missing required consent input for {CONSENT TYPE}: {what}. Re run and provide it. (missing consent input)
Error: {kind}: {message} (other failures)
Worked examples
For reference runs of the ImplicitOptIn (opt out only), ExplicitOptIn, and DoubleOptIn paths, see references/worked examples.md .
Gotchas
Known gotchas — the exact per ConsentType activation readiness contract (and its source), comma separated keyword storage, the "ImplicitOptIn still needs a keyword record" trap, one record per language uniqueness, the Unified SMS help/French custom rules, and the OptInPrompt Unified SMS/WhatsApp/RCS exemption.
When troubleshooting an unexpected result, or before modifying this skill, load references/gotchas.md and follow it.