Skip to content

Social: default share-message meta to the saved template server-side#48634

Merged
gmjuhasz merged 7 commits intotrunkfrom
fix/social/message-box-ux
May 11, 2026
Merged

Social: default share-message meta to the saved template server-side#48634
gmjuhasz merged 7 commits intotrunkfrom
fix/social/message-box-ux

Conversation

@manzoorwanijk
Copy link
Copy Markdown
Member

@manzoorwanijk manzoorwanijk commented May 8, 2026

Closes SOCIAL-481.

Proposed changes

Move template-fallback responsibility for the share-message and per-connection message from the editor to the server, so the editor renders the meta verbatim and an empty stored value is correctly interpreted as "fall back to the template" by the renderer.

The field can now actually be cleared without snapping back to the template — the bug introduced by SOCIAL-479's editor-side pre-fill — and the editor's customization forms / preview render hooks no longer need to know about templates at all.

  • class-publicize-base.phpregister_post_meta() resolves the share-message default from Settings::get_message_template() once on init priority 20 (gated on Current_Plan::supports( 'social-message-templates' )) and passes it as register_meta's 'default'. Avoids the hot-path cost of hooking default_post_metadata. Falls back to '' on non-template sites — the legacy extractor would otherwise treat a raw template as literal share text.
  • class-connections-post-field.php — defaults connection.message to the connection's own template (when set) regardless of per-network mode, so the editor receives the connection-template fallback up front. Without this, syncConnections (which fires on per-network toggle) would treat connection.message === undefined as "uncustomized" and silently copy the post-level share message over the connection's own template. Per-network override message, when present, still takes precedence.
  • useRenderMessageItems / useConnectionPreviewData — drop the messageTemplate selector reads and the connection.message ?? connection.template ?? globalMessage fallback chain. Both hooks collapse to "use connection.message in per-network mode, otherwise globalMessage", with a ?? globalMessage guard for connections that have neither override nor template.
  • customization-forms/global.tsx — drop the useSocialMediaMessage + messageTemplate read and the shareMessage || messageTemplate pre-fill. SharePostForm's default already wires useSocialMediaMessage internally, and an empty shareMessage is now the right thing to display.
  • customization-forms/per-network.tsx — drop the three-way help text and the connection.template ?? globalMessage fallback chain. Display rule collapses to connection.message ?? globalMessage, and the help text becomes a single sentence.
  • use-per-network-customization.ts — rework syncConnections. The "uncustomized" outer guard switches from connection.message === undefined to connection.media_source !== undefined — message is now server-defaulted to connection.template, so it no longer indicates customization, but media fields are only written when the user (or a prior sync) has explicitly set them. The ! connection.template skip from the prior commit chain is preserved so the post-level share message doesn't overwrite the connection-template contribution to connection.message.

Related product discussion/links

Does this pull request change what data or activity we track or use?

No.

Testing instructions

Set up a test site with the message-templates feature enabled and at least two social connections.

Test it along with 215588-ghe-Automattic/wpcom

Site-wide template fallback (global mode):

  1. On the Social admin page, set a Main Template (e.g., {title} — read more at {url}).
  2. Open a new post in the block editor. Open the Social customization modal.
  3. The share-message field should display the saved template as its initial value.
  4. Clear the field. Save the post.
  5. Reopen the post. The field should remain empty (no snap-back to the template).
  6. Publish/share. The post should be shared using the template at render time.

Per-connection template fallback:

  1. Set a per-connection template for one of your connections (e.g., Facebook gets Hey FB folks: {title}).
  2. Open a new post in the block editor. Toggle per-network customization on.
  3. The Facebook tab's message field should display its connection template; other connections show the global template.
  4. Clear the Facebook field. The field should stay empty without bouncing back to the connection template.
  5. Save and reload — cleared field stays cleared.

syncConnections doesn't overwrite per-connection templates:

  1. With a per-connection template configured for Facebook (and the global template also set), open a fresh post.
  2. Toggle per-network on.
  3. Confirm the Facebook tab shows its connection template (not the global template) in the message field.
  4. Confirm the Facebook media UI matches the preview (no featured-image / SIG mismatch).

Non-template-mode sites unaffected:

  1. On a site without the message-templates feature, repeat the basic share flow.
  2. The share-message field starts empty (no raw {title} literal injection), and shares fall back to the post title as before.

Before / After

Before After

@manzoorwanijk manzoorwanijk marked this pull request as draft May 8, 2026 07:30
@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented May 8, 2026

Are you an Automattician? Please test your changes on all WordPress.com environments to help mitigate accidental explosions.

  • To test on WoA, go to the Plugins menu on a WoA dev site. Click on the "Upload" button and follow the upgrade flow to be able to upload, install, and activate the Jetpack Beta plugin. Once the plugin is active, go to Jetpack > Jetpack Beta, select your plugin (Jetpack), and enable the fix/social/message-box-ux branch.
  • To test on Simple, run the following command on your sandbox:
bin/jetpack-downloader test jetpack fix/social/message-box-ux

Interested in more tips and information?

  • In your local development environment, use the jetpack rsync command to sync your changes to a WoA dev blog.
  • Read more about our development workflow here: PCYsg-eg0-p2
  • Figure out when your changes will be shipped to customers here: PCYsg-eg5-p2

@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented May 8, 2026

Thank you for your PR!

When contributing to Jetpack, we have a few suggestions that can help us test and review your patch:

  • ✅ Include a description of your PR changes.
  • ✅ Add a "[Status]" label (In Progress, Needs Review, ...).
  • ✅ Add testing instructions.
  • ✅ Specify whether this PR includes any changes to data or privacy.
  • ✅ Add changelog entries to affected projects

This comment will be updated as you work on your PR and make changes. If you think that some of those checks are not needed for your PR, please explain why you think so. Thanks for cooperation 🤖


Follow this PR Review Process:

  1. Ensure all required checks appearing at the bottom of this PR are passing.
  2. Make sure to test your changes on all platforms that it applies to. You're responsible for the quality of the code you ship.
  3. You can use GitHub's Reviewers functionality to request a review.
  4. When it's reviewed and merged, you will be pinged in Slack to deploy the changes to WordPress.com simple once the build is done.

If you have questions about anything, reach out in #jetpack-developers for guidance!

@github-actions github-actions Bot added the [Status] Needs Author Reply We need more details from you. This label will be auto-added until the PR meets all requirements. label May 8, 2026
@jp-launch-control
Copy link
Copy Markdown

jp-launch-control Bot commented May 8, 2026

Code Coverage Summary

Coverage changed in 8 files. Only the first 5 are listed here.

File Coverage Δ% Δ Uncovered
projects/packages/publicize/_inc/hooks/use-render-message-items/index.ts 40/54 (74.07%) -4.61% 1 ❤️‍🩹
projects/packages/publicize/src/class-publicize-base.php 293/648 (45.22%) 0.10% 1 ❤️‍🩹
projects/packages/publicize/src/rest-api/class-connections-post-field.php 226/276 (81.88%) -0.17% 1 ❤️‍🩹
projects/packages/publicize/_inc/components/customize-and-preview/customization-forms/per-network.tsx 10/12 (83.33%) -8.97% 0 💚
projects/packages/publicize/_inc/hooks/use-post-meta/index.js 27/28 (96.43%) 0.27% 0 💚

Full summary · PHP report · JS report

@manzoorwanijk manzoorwanijk force-pushed the fix/social/message-box-ux branch from 81179e1 to 0536252 Compare May 8, 2026 08:05
@manzoorwanijk manzoorwanijk force-pushed the fix/social/message-box-ux branch from 40e6067 to 0536252 Compare May 8, 2026 10:12
@manzoorwanijk manzoorwanijk changed the title Social: default share-message meta to the saved template server-side (SOCIAL-481) Social: default share-message meta to the saved template server-side May 8, 2026
@manzoorwanijk manzoorwanijk force-pushed the fix/social/message-box-ux branch from 0536252 to ac621c8 Compare May 8, 2026 10:30
manzoorwanijk and others added 4 commits May 8, 2026 16:05
…OCIAL-479)

Move template-fallback responsibility from the editor to the server so
the editor can render `_wpas_mess` and `connection.message` verbatim
instead of mirroring the renderer's fallback chain client-side. An
empty stored value now cleanly means "user explicitly cleared", and the
renderer (WPCOM extractor) handles the actual template substitution at
share time.

- `class-publicize-base.php`: in `register_post_meta()`, resolve the
  share-message default from `Settings::get_message_template()` once on
  init priority 20 (gated on `Current_Plan::supports( 'social-message-templates' )`)
  and pass it as `register_meta`'s `'default'`. Avoids hooking
  `default_post_metadata`, which fires on every unset post-meta lookup
  across the request. Falls back to `''` on non-template sites — the
  legacy extractor would otherwise treat a raw template as literal
  share text.

- `class-connections-post-field.php`: default `connection.message` to
  the connection's own `template` (when set) regardless of per-network
  mode, so the editor receives the connection-template fallback up
  front. Without this, `syncConnections` (which fires on per-network
  toggle) would treat `connection.message === undefined` as
  "uncustomized" and silently copy the post-level share message over
  the connection's own template. Per-network override `message`, when
  present, still takes precedence. No fallback to the saved global
  template here — that's the post-level `_wpas_mess`'s job, with the
  editor's `connection.message ?? globalMessage` chain bridging the two.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…AL-479)

`connection.message` and the post-level `globalMessage` are now
server-side defaulted to the appropriate template (parent commit), so
the editor-side fallback chains in `useRenderMessageItems` and
`useConnectionPreviewData` collapse to "use connection.message in
per-network mode, otherwise globalMessage" with a `?? globalMessage`
guard for connections that have neither override nor connection
template. The `messageTemplate` selector reads and the
`hasConnectionMessage`/`connection.template` branching in both hooks
are gone.

The two hooks must agree exactly so `currentRenderItem.message`
matches `baseMessage` and `isDebouncingRenderedMessage` doesn't stay
stuck true after toggling per-network → global; the simplified
expression is identical in both call sites.

Test fixture in `useConnectionPreviewData` updated to drop the now-
absent `messageTemplate` mock entry from the chained `useSelect`
sequence.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
)

The two prior commits move template-fallback responsibility to the
server, so the editor's customization forms can render the meta
verbatim and stop reaching for the saved template option.

global.tsx: drop the `useSocialMediaMessage` + `messageTemplate` read
+ `shareMessage || messageTemplate` pre-fill. SharePostForm's default
already wires `useSocialMediaMessage` internally, and an empty
`shareMessage` is the right thing to display now that the renderer
handles the fallback.

per-network.tsx: drop the `connection.template ?? globalMessage`
fallback chain, the `messageTemplate` read, and the three-way help
text. Display rule collapses to `connection.message ?? globalMessage`
— `connection.message` is server-defaulted to the connection's own
template when no override exists, and globalMessage covers the no-
template case. Help text becomes a single sentence; the editor no
longer needs to know which template tier will apply.

use-per-network-customization.ts: rework `syncConnections`. The
"uncustomized" outer guard switches from `connection.message ===
undefined` to `connection.media_source !== undefined` — message is
now server-defaulted to `connection.template`, so it no longer
indicates customization, but media fields are only written when the
user (or a prior sync) has explicitly set them. The
`! connection.template` skip from 8d92d39 is preserved so the
post-level share message doesn't overwrite the connection-template
contribution to `connection.message`.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@manzoorwanijk manzoorwanijk force-pushed the fix/social/message-box-ux branch from ac621c8 to a132811 Compare May 8, 2026 10:36
@manzoorwanijk manzoorwanijk marked this pull request as ready for review May 8, 2026 10:42
@manzoorwanijk manzoorwanijk requested a review from gmjuhasz May 8, 2026 10:42
@manzoorwanijk manzoorwanijk added [Status] Needs Team Review Obsolete. Use Needs Review instead. and removed [Status] Needs Author Reply We need more details from you. This label will be auto-added until the PR meets all requirements. labels May 8, 2026
manzoorwanijk and others added 2 commits May 8, 2026 19:07
…AL-479)

In per-network mode, fall back to the saved site message template
(not `globalMessage` / `_wpas_mess`) when the connection has no
per-post override and no connection-template default. The form
itself is bound strictly to `connection.message` — the site-template
fallback is applied only at preview-render time, so the field stays
editable and a cleared value is preserved as `''`.

- `per-network.tsx`: drop the `connection.message ?? globalMessage`
  chain; bind the field to `connection.message ?? ''`. Cleared
  messages stay cleared.

- `useRenderMessageItems` / `useConnectionPreviewData`: read
  `siteMessageTemplate` from the social store and use it as the
  per-network fallback in `connection.message ?? siteMessageTemplate`.
  Global mode keeps `globalMessage`. Both hooks compute the same
  chain so `currentRenderItem.message` matches `baseMessage` and
  `isDebouncingRenderedMessage` doesn't get stuck.

- `useRenderMessageItems`: combine the two `useSelect` calls
  (connections + siteMessageTemplate) into one for clarity. Test
  fixture switches to a `mockSelect` helper that returns the merged
  shape.

- `useConnectionPreviewData` test: extend the chained `useSelect`
  mock with the new `messageTemplate` slot.

- `per-network.test.tsx`: assert the new no-fallback form rule
  (cleared / unset connection.message → empty field, not globalMessage).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Copy link
Copy Markdown
Contributor

@gmjuhasz gmjuhasz left a comment

Choose a reason for hiding this comment

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

It tests well with all the mentioned scenarios

@gmjuhasz gmjuhasz merged commit 3bdbf08 into trunk May 11, 2026
75 checks passed
@gmjuhasz gmjuhasz deleted the fix/social/message-box-ux branch May 11, 2026 11:39
@github-actions github-actions Bot added [Status] UI Changes Add this to PRs that change the UI so documentation can be updated. and removed [Status] Needs Team Review Obsolete. Use Needs Review instead. labels May 11, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

[Feature] Publicize Now Jetpack Social, auto-sharing [Package] Publicize [Package] Sync [Status] UI Changes Add this to PRs that change the UI so documentation can be updated. [Tests] Includes Tests

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants