Skip to content

Skip cloneElement for Fragment children in TouchableHighlight#56539

Open
qflen wants to merge 2 commits intofacebook:mainfrom
qflen:fix/touchable-highlight-fragment-54933
Open

Skip cloneElement for Fragment children in TouchableHighlight#56539
qflen wants to merge 2 commits intofacebook:mainfrom
qflen:fix/touchable-highlight-fragment-54933

Conversation

@qflen
Copy link
Copy Markdown
Contributor

@qflen qflen commented Apr 21, 2026

Summary

Fixes #54933.

Passing a React.Fragment as the child of TouchableHighlight currently produces this warning:

Warning: Invalid prop style supplied to React.Fragment.
React.Fragment can only have key and children props.

This happens because TouchableHighlight unconditionally calls cloneElement(child, {style}) on its single child, including when that child is a Fragment.

This PR skips that clone when child.type === React.Fragment and renders the Fragment as-is.

That avoids passing an invalid style prop to React.Fragment while preserving the existing render path for Fragment children.

Changelog:

[General] [Fixed] - Suppress React.Fragment style warning when used as a child of TouchableHighlight

Test Plan

  • Added a Fantom regression test in TouchableHighlight-itest.js that renders <TouchableHighlight><Fragment>...</Fragment></TouchableHighlight>
  • Verified the expected rendered output
  • Verified console.error is not called
  • yarn flow focus-check packages/react-native/Libraries/Components/Touchable/TouchableHighlight.js
  • yarn lint on the changed files
  • yarn prettier --list-different on the changed files

@meta-cla
Copy link
Copy Markdown

meta-cla Bot commented Apr 21, 2026

Hi @qflen!

Thank you for your pull request and welcome to our community.

Action Required

In order to merge any pull request (code, docs, etc.), we require contributors to sign our Contributor License Agreement, and we don't seem to have one on file for you.

Process

In order for us to review and merge your suggested changes, please sign at https://code.facebook.com/cla. If you are contributing on behalf of someone else (eg your employer), the individual CLA may not be sufficient and your employer may need to sign the corporate CLA.

Once the CLA is signed, our tooling will perform checks and validations. Afterwards, the pull request will be tagged with CLA signed. The tagging process may take up to 1 hour after signing. Please give it that time before contacting us about it.

If you have received this in error or have any questions, please contact us at cla@meta.com. Thanks!

@meta-cla meta-cla Bot added the CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. label Apr 21, 2026
@facebook-github-tools facebook-github-tools Bot added the Shared with Meta Applied via automation to indicate that an Issue or Pull Request has been shared with the team. label Apr 21, 2026
@github-actions
Copy link
Copy Markdown

Warning

JavaScript API change detected

This PR commits an update to ReactNativeApi.d.ts, indicating a change to React Native's public JavaScript API.

  • Please include a clear changelog message.
  • This change will be subject to additional review.

This change was flagged as: POTENTIALLY_BREAKING

@javache
Copy link
Copy Markdown
Member

javache commented May 6, 2026

This will break the highlight though. Would it better to generate a more actionable error here (eg TouchableHighlight doesn't support fragments)?

@qflen
Copy link
Copy Markdown
Contributor Author

qflen commented May 6, 2026

Hm, I will check.

@qflen qflen force-pushed the fix/touchable-highlight-fragment-54933 branch from b7f1c1b to 0f69734 Compare May 6, 2026 13:22
Fixes facebook#54933.

TouchableHighlight injects the underlay style onto its single child via
cloneElement. React.Fragment cannot accept that style, so React emits a
generic "Invalid prop `style` supplied to `React.Fragment`" warning and
the highlight effect is silently broken.

Surface a clear console.error in __DEV__ naming the component, the
constraint, and the fix (wrap in a View). Skip the cloneElement when
the child is a Fragment so React's generic warning no longer fires on
top. Render the Fragment unchanged so apps relying on this since 0.79
do not crash on upgrade. Pattern matches dev error logging used
elsewhere in RN such as ScrollView and TextInputState.
@qflen qflen force-pushed the fix/touchable-highlight-fragment-54933 branch from 0f69734 to 85e74eb Compare May 6, 2026 13:31
@qflen
Copy link
Copy Markdown
Contributor Author

qflen commented May 6, 2026

@javache Right, the previous version silenced the warning while leaving the highlight broken.

Update logs a clear console.error in __DEV__ when the child is a React.Fragment.

The message names the component, the constraint, and the fix (wrap in a <View>), mirroring the existing class doc and the dev error pattern used elsewhere in RN (ScrollView, TextInputState). The Fragment is still rendered unchanged so apps that have been silently rendering it since 0.79 do not crash on upgrade.

An alternative would be to switch to a hard invariant throw if a stricter contract is preferred, like:

invariant(
  child.type !== React.Fragment,
  'TouchableHighlight does not support React.Fragment as a child. ' +
    'Wrap the children in a single host element such as <View>.',
);

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. Shared with Meta Applied via automation to indicate that an Issue or Pull Request has been shared with the team.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

As of 0.79, you can't put a Fragment in a TouchableHighlight without a warning

2 participants