Summary:
## Problem
Many of our NativeModules are TurboModule-compatible. All our TurboModules currently use the bridge to require other NativeModules/TurboModules. As we migrate more surfaces to Venice, this lookup in many of these TurboModules will break, because the bridge will be nil.
## Initial Solution
We migrate all these TurboModules over to the turboModuleRegistry. In FBiOS, this will work because all NativeModules are TurboModule-compatible, and should [have the turboModuleRegistry attached to them by the TurboModuleManager](https://fburl.com/diffusion/d747fbc3). However, this solution has a few problems:
- If the TurboModule is used within a TurboModule-disabled app, it will break, because turboModuleRegistry will be nil on the module. Therefore, this solution isn't portable/flexible across apps.
- Longer term, we should deprecate synthesize bridge inside NativeModules. With this approach, we can't remove the synthesize bridge = bridge call from the NativeModule.
## Suggested Solution
Both NativeModules and TurboModules will be given access to an `RCTModuleRegistry` object. The RCTModuleRegistry object will use the TurboModuleManager when available and the Bridge when available to query for NativeModules and TurboModules. Otherwise, it'll just return nil.
When we do a lookup via this RCTModuleRegistry:
- In Venice, the bridge will be nil, so we won't search the bridge.
- In FBiOS, the bridge and the TurboModuleManager will be non-nil, so we'll first search the bridge, and then the TurboModuleManager.
- In standalone apps, the TurboModuleManager will be nil, so we'll only do a lookup on the bridge.
Long story short, RCTModuleRegistry will do the right thing in all scenarios.
Changelog: [Internal]
Reviewed By: PeteTheHeat
Differential Revision: D25412847
fbshipit-source-id: 13f41276158d90c68ab4925e518d71a2f369c210
Summary:
This fix is still a little hypothetical. We have a few different JS errors that we're seeing with bridgeless mode that seem to be caused by Fabric trying to access `__fbBatchedBridge` from C++. I think what's happening is:
1. User encounters an unrelated JS error very early in rendering a new surface (possibly while the bundle is still loading?)
2. In release builds, BridgelessReactFragment handles the error by stopping the surface and rendering a retry button (actually, the surface is stopped in a bunch of places in BaseFbReactFragment, which might be why this is popping up now - I recently refactored that class to share more of its logic in bridgeless mode)
3. Fabric stops the surface by first checking to see if the custom binding `RN$stopSurface` exists; if not, it falls back to calling the registered callable module `ReactFabric`.
I think #3 is where things are going wrong for bridgeless mode; if you call stopSurface before `RN$stopSurface` is installed (which happens when ReactFabric shim is required) then you'll fall back to the bridge version.
My solution here is to instead rely on a flag set in C++ to determine whether we're in bridgeless mode, and then check to see if the stopSurface binding has been installed. If not, we just noop - if the ReactFabric shim hasn't been required, we probably don't actually have a React surface that needs to be stopped.
At least, that's my current theory. We'll see if this actually works.
Changelog: [Fixed][iOS] Fix an issue calling stopSurface in bridgeless mode before surface is started
Reviewed By: mdvacca
Differential Revision: D25453696
fbshipit-source-id: bff76675c43989101d0ba5ae0aba60089db230bf
Summary:
Some of the existing files under uimanager/ are self contained and used by the component codegen output. This commit split out those files into a dedicated uimanager/interfaces/ dir/target so that more targets can depend on it without causing dep cycle.
Also, the component codegen output doesn't need LayoutShadowNode at all, so this removed the import.
This will allow us to combine the Java codegen output for TM spec and Fabric components, simplifying build and dependency management (not in this commit yet).
Changelog: [Internal]
Reviewed By: JoshuaGross
Differential Revision: D25451409
fbshipit-source-id: 827545a3d78ebed1815cf9e52da2fa896b012aa1
Summary:
The flag `clipChildRectsIfOverflowIsHidden` has been set to false for a little over a year. Delete it and associated callsites.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D25451696
fbshipit-source-id: a6067b2e25124f6bdef336c2ddead719dd44cca9
Summary:
In practice this has been enabled in production for months and is fine. Remove feature-flag and gating.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D25451697
fbshipit-source-id: 9e70db3ed4e00de7b8295d9225d43ba09e4e68e9
Summary:
This has been true for 100% of users for months; clean up the old code.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D25451470
fbshipit-source-id: feae59ce746869b9d84d6aaa69be10e91181f03a
Summary:
This code was useful for debugging T78035906 but is no longer needed.
I'm a bit conflicted about removing it, since such issues could crop up again in the future - but they're very rare, and hopefully now we know how to avoid them.
tl;dr: Make sure that mount instructions are not executed *during* a draw or measure.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D25450846
fbshipit-source-id: e261f13db252d22773e373a5de744ecc8c380a43
Summary:
This code and this class isn't needed in Fabric, so don't create it during construction. Lazy-load it when it's needed outside of Fabric.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D25450724
fbshipit-source-id: d14d8f03c194716f2aba0e499f3282ad2d1c1d29
Summary:
This commit:
* Generate Fabric component Java files along side Java NativeModule specs, when `USE_FABRIC=1` is set
* Adjust the component codegen to place output files in a subdir based on package name
* Adjust existing Buck targets to filter the right nativemodule vs component java files (this avoids duplicated symbols)
* Compiles the Java output during build time on RNTester/ReactAndroid (Gradle)
Not in this commit:
* Fabric C++ files
* Removing checked-in generated component files.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D25416614
fbshipit-source-id: fd670ead2198c9b5a65812c692b7aed9f3d7cd58
Summary:
Changelog: [internal]
In D25386708 (https://github.com/facebook/react-native/commit/408bcdeedbc89cc9b90de73684d3f691b8e2e724) `synthesize bridge` was removed. But two modules actually depend on this.
`RCTFileReaderModule` and `VerseThreadView` which both use it.
Reviewed By: RSNara
Differential Revision: D25423574
fbshipit-source-id: daf95d9b27841cf8d205d8ea2666d5aa69a6d720
Summary:
This diff prevents the pre-calculation of ViewManager's constants for users with static view config enabled.
We still load viewManager classes and create viewManger objects for perf reasons
Changelog: [Internal]
Reviewed By: fkgozali
Differential Revision: D25414068
fbshipit-source-id: a91f6113e35b42625c03d13bd67b63e3f9f75098
Summary:
This is a codemod. All these NativeModules demand access to the bridge. However, they don't use it.
Changelog: [Internal]
Reviewed By: PeteTheHeat, RoelCastano
Differential Revision: D25386708
fbshipit-source-id: f05f4777d2527e96e53581e7ac58f6be47411dce
Summary:
There is partially compiled TurboModule code in [NativeAnimatedModule](https://fburl.com/diffusion/g91a70ng) that fails to build with:
`"File neither contains a module declaration, nor a component declaration. For module declarations, please make sure your file has an InterfaceDeclaration extending TurboModule. For component declarations, please make sure your file has a default export calling the codegenNativeComponent<Props>(...) macro"`
This diff removes react-native-web from the TurboModules logic while we work on a cleaner solution, tracked in T80868008
msdkland[metro]
Changelog: [Internal]
Reviewed By: cpojer, RSNara
Differential Revision: D25325163
fbshipit-source-id: 346abf52660073f976b0f978cbfbfc8402f4b3ee
Summary:
Cleanup release.gradle and remove code used to upload RN to maven repository, which is not longer used. Also removed configuration to include Javadoc, Sources in maven repo, thus reduce NPM package size.
## Changelog
[Internal] [Changed] - cleanup and remove maven upload from release.gradle
Pull Request resolved: https://github.com/facebook/react-native/pull/30468
Test Plan: you will no longer see *uploadArchives* in ./gradlew tasks. Also you can run **./gradlew :ReactAndroid:installArchives**
Reviewed By: mdvacca
Differential Revision: D25408128
Pulled By: fkgozali
fbshipit-source-id: b3ced1b466b9f11e3970136a116af4e29dbd33a1
Summary:
Added examples to RNTester for the AccessibilityInfo API for:
1. SetAccessibilityFocus()
2. isReduceMotionEnabled()
3. iOS Only
a. isBoldTextEnabled()
b. isGrayScaleEnabled()
c. isInvertColorsEnabled()
d. isReduceTransparencyEnabled()
## Changelog
<!-- Help reviewers and the release process by writing your own changelog entry. For an example, see:
https://github.com/facebook/react-native/wiki/Changelog
-->
[General] [Added] - Add new examples to the Accessibility API page
Pull Request resolved: https://github.com/facebook/react-native/pull/30379
Test Plan: 
Reviewed By: TheSavior
Differential Revision: D25245329
Pulled By: rickhanlonii
fbshipit-source-id: e9c11c775410075199b4e1011b3dac0acd972e89
Summary:
When calling the original console methods we should set this to the value of the original console. Otherwise this can lead to different behaviour between when the debugger is enabled or not.
Changelog: [Internal]
Reviewed By: mhorowitz
Differential Revision: D25367929
fbshipit-source-id: 0a7b65e501d4460d5e09a7ccd3c38ef61fbd2ef0
Summary:
As part of the initialization of Native View configs, the PaperUIManager.getViewManagerConfig() method calls the native side to lazy initialize iOS Native components. This is necessaary to make ensure that native classes are loaded and initialized before a view is created.
Note that this requirement is only necessary when Fabric is disabled.
As part of JS ViewConfigs, we removed the native call to lazy initialize iOS native components. This causes a crash during the creation of NativeViews when JS ViewConfigs are enabled and Fabric is disabled. The rootcase of the exception is that native classes are not properly initialized when the createView method is executed in iOS.
This diff forces the lazy initialization of iOS Native components when JS View configs are enabled and Fabric is disabled. This new mechanism is executed as part of the creation of views and it's ONLY going to be executed when the user navigates to a NON-FABRIC screen, JS ViewConfigs are enabled and the component is not initialized yet.
The extra cost should be minimal or zero.
changelog: [internal] internal
Reviewed By: fkgozali
Differential Revision: D25387014
fbshipit-source-id: fe3bc42f803a805192b419bfb4b7a6b5b1b71b60
Summary:
Instead of doing a "containsKey then get", just get the rootViewTag and see if it's non-null. Theoretically, since it's a
concurrent data-structure, it could be removed from the ConcurrentHashMap between "containsKey" returning true and the "get".
This does not fix any known, existing problems.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D25378703
fbshipit-source-id: 62a44e68e4443dac5a557263cc4bb33de9eea993
Summary:
There is an optimization in FabricUIManager.surfaceActiveForExecution that ensures it returns the same value (true or false)
for a given SurfaceId for a single frame (the value is cached until the next frame).
It seems like this can be causing a few different crashes, in a couple different ways:
1) If StopSurface is called off the UI thread, in the middle of a batch of operations (probably less likely to cause problems)
2) If StopSurface is called on the UI thread, in between different operations; the latter operations will still execute because the `true` value of `surfaceActiveForExecution` was cached.
I don't think that this optimization was providing much for us, and could be causing crashes. Remove it for now and we'll analyze impact on crashes and perf.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D25379970
fbshipit-source-id: 2c15c971bd0c828e1d38a34662d93293271041b2
Summary:
The `BlobCollector` native module stored a `jni::global_ref` as a member,
and its destructor automatically destroys it.
However, as noted in JSI documentation, there is no guarantee that the destructor
is run on a JVM-registered thread. The destructor knew this and used a `jni::ThreadScope`
to do some other JNI behavior, but the global_ref needs to be destroyed during
that ThreadScope as well.
Changelog: [Internal]
Reviewed By: neildhar
Differential Revision: D25372698
fbshipit-source-id: f4eba0b2da154c6eac54d7faeb9ea5bb9260bec9
Summary:
The `index` parameter for UpdateMutation is optional, and is normally just -1. It's not useful, so remove it. `parentShadowView` is also not relevant and is not used; in some existing use-cases the actual parent view of the updated view is available, and in some contexts the parent view is not set.
The function now will always set the index to -1 for UpdateMutations, and `{}` for ParentShadowView.
This should have no impact on iOS or Android, as this parameter is not used. It could theoretically have an impact on lifetimes of objects retained (now not retained) by not passing parentShadowView into the mutation. For example, any shared props or state associated with the parent will not be retained in the Update mutation now.
Changelog: [Internal]
Reviewed By: shergin
Differential Revision: D25342943
fbshipit-source-id: 0ddbef76a6e2eefc2629c9729f721d8674d7737e
Summary:
UserFlow API now takes configuration parameter, which is required. It contains of 2 arguments:
* triggerSource
* cancelOnBackround
Reviewed By: swillard13
Differential Revision: D25094721
fbshipit-source-id: 64a468c2168265ade9f8d4cea4beb911637544fa
Summary:
Props are transferred from C++ to Java using ReadableNativeMaps. The current implementation of ReadableNativeMaps creates an internal HashMap the first time one of its methods is executed.
During the update of props ReadableNativeMaps are consumed only once and they are accessed through an Iterator. That's why there is no reason to create the internal HashMap, which is inefficient from performance and memory point of view.
This diff creates an experiment that avoids the creation of the internal HashMap during prop updates, additionally it removes a lock that was being used in the creation of the internal HashMap. I expect this change to have a positive impact in TTRC and memory (in particular for ME devices)
This diff reduces the amount of ReadableNativeMaps's internal HashMaps created during initial render of MP Home by ~35%.
Changelog: [Internal]
Reviewed By: JoshuaGross
Differential Revision: D25361169
fbshipit-source-id: 7b6efda11922d56127131494ca39b5cec75f1703
Summary:
Add missing examples to ScrollView for RNTester.
## Changelog
<!-- Help reviewers and the release process by writing your own changelog entry. For an example, see:
https://github.com/facebook/react-native/wiki/Changelog
-->
[General] [Added] - Add missing examples to ScrollView for RNTester.
Pull Request resolved: https://github.com/facebook/react-native/pull/30454
Test Plan: There are a lot of examples that have been added that affects the UI (see RNCore Excel sheet for details).
Reviewed By: sammy-SC
Differential Revision: D25310613
Pulled By: rickhanlonii
fbshipit-source-id: 64a771aa8d3c3683eed983b0c36625078e5533fe
Summary:
The root cause of this bug is a race condition between the onMeasure method and setupReactContext.
ReactInstanceManager.attachRootView() method is responsible of the initialization of ReactRootViews and it is invoked by ReactRootView.onMeasure() method in the UIThread
Important initialization steps:
1. Clear the Id of the ReactRootView
2. Add the ReactRootView to the mAttachedReactRoots
3. Call StartSurface (if the bridge has been initialized)
Sometimes, when this method is invoked for the first time, the bridge is not initialized, in those cases we delay the start of the surface.
Once the bridge is initialized, StartSurface is called by the setupReactContext() running in the NativeModuleThread.
Since onMeasure can be called multiple times, it is possible that we call "StartSurface" twice for the same ReactRootView, causing the bug reported on T78832286.
This diff adds an extra check to prevent calling "StartSurface" twice. The fix is done using an AtomicInteger comparison and it is gated by the flag "enableStartSurfaceRaceConditionFix". Once we verify this works fine in production we will clean up the code, remove the flags and maybe revisit the API of ReactRoot.
changelog: [Android] Fix race-condition on the initialization of ReactRootViews
Reviewed By: JoshuaGross
Differential Revision: D25255877
fbshipit-source-id: ca8fb00f50e86891fb4c5a06240177cc1a0186d9
Summary:
`RCTAlertController` creates a new window, and presents itself in that window.
RCTAlertController strongly retains the window, and the window strongly retains RCTAlertController when presenting it.
This adds a new method to break that cycle once alert is dismissed.
Changelog: [Internal]
Reviewed By: shergin
Differential Revision: D25312413
fbshipit-source-id: e4048922aa697eb42c4c149827bac61bc7bc5528
Summary:
If a ShadowNode is being animated from opacity 0 to 1, and that animation is interrupted by another update to the same ShadowNode, we stop the animation and send the original "final" ShadowView
to the mounting layer. On iOS, this is enough to make the Mounting layer consistent with the Shadow layer. However, on Android, since only prop deltas are passed to the mounting layer and not the
entire props bag, this will NOT be enough because the opacity will not be updated in that final step.
Therefore, in those cases where we've detected a conflict and we're cleaning up after an interrupted animation, we must send two updates to the mounting layer: one to force the opacity to 1,
and another to make the ShadowTree consistent with the Mounting layer.
Changelog: [Internal]
Reviewed By: sammy-SC
Differential Revision: D25324942
fbshipit-source-id: 5d9666128feaae87d7530c394ef05db580aa5a75
Summary:
In the Codegen, we need to answer the following questions:
*Question:* What are all the calls into TurboModuleRegistry?
*Answer:* Find all CallExpressions that represent TurboModuleRegistry.get<Spec>() or TurboModuleRegisty.getEnforcing<Spec>().
*Question:* Is this a component spec?
*Answer:* Does this spec have a CallExpression where the callee is 'codegenNativeComponent'?
*Question:* Is this a module spec?
*Answer:* Does this spec have an interface that extends TurboModule?
All these answers can be implemented using the visitor pattern. Hence, this diff introduces the `visit` utility, and uses it to answer these questions.
**Motivation:** Cleaner code.
Changelog: [Internal]
Reviewed By: hramos
Differential Revision: D25162617
fbshipit-source-id: 66ec95fc07ecb29aa9bf9993cb826204af283d03
Summary:
**Motivation:** After this change, we can show this ParserError using the React Native Module ESLint rule. Previously when we declared more than one NativeModule spec in a file, we incorrectly reported that there were *no* NativeModule specs in the file.
Changelog: [Internal]
Reviewed By: hramos
Differential Revision: D25163299
fbshipit-source-id: 92bc09d09cdbc323e0ac1f317c40a767880f5bc2
Summary:
## What is `guard`?
`guard` accepts some JavaScript function that can throw a ParserError. If a ParserError is thrown by that JavaScript function, it captures and pushes the error to some global array, and returns null. If no ParserError is thrown, it simply returns the return value of the JavaScript function. This utility is used in the NativeModule spec parser to help it continue parsing even after it detects errors. Why do we want to do this? In the NativeModule spec linter, we want to display all these ParserErrors via ESLint.
## Changes
This diff renames `guard` to `tryParse` because `tryParse` more appropriately captures the intent/function of this utility: the work passed to it "tries" to parse some Flow types. A name like "guard" is a bit more ambiguous: What is it guarding against? What is the work doing? ¯\_(ツ)_/¯
Changelog: [Internal]
Reviewed By: hramos
Differential Revision: D25156185
fbshipit-source-id: 516647770579daa8613dbd67535074823f1aa848
Summary:
## Changes
1. In the NativeModule spec parser, the moduleName is now being extracted from the TurboModuleRegistry.get<Spec>(...) call by examining the Flow ast node. Previously, we used regex parsing, which was unsafe because it could be fooled by TurboModuleRegistry.get<Spec>(...) calls in comments.
2. The logic to parse and validate the TurboModuleRegistry.get<Spec>(...) call is now centralized in the NativeModule Spec Parser (it was removed from the react-native-modules ESLint rule). The linter is now only responsible for three things:
1. Detecting if a JavaScript file contains a TurboModuleRegistry.get<Spec> call or a TurboModule interface, and if so
2. Running the NativeModule spec parser on it.
3. It also validates that the Module spec's filename starts with the prefix "Native".
The React Native Modules linter now completely delegates to the NativeModules Spec parser, without doing any error checking of its own. If an error is reported by the React Native Modules linter, and that error doesn't have anything to do with the "Native" prefix, then it *must* be addressed. Otherwise, it will cause the NativeModule Spec Parser to fail on that particular spec.
Changelog: [Internal]
Reviewed By: hramos
Differential Revision: D25153243
fbshipit-source-id: da74dbb66b1d8dca3a2b1952402222c6696b73d6
Summary:
this diff fixes the next error:
```
'RCTImageView' has a view config that does not match native. 'validAttributes' is missing: internal_analyticTag
in RCTImageView (at Image.ios.js:149)
in ImageAnalyticsTagContext.Consumer (at Image.ios.js:146)
in Image (at TintedIcon.js:55)
in TintedIcon (at TetraIcon.js:98)
in TetraIcon (at FDSCheckbox.js:67)
in FDSCheckbox (at TetraListCell.js:820)
in TetraAddOnSecondary (at TetraListCell.js:576)
in TetraPressable (at TetraListCell.js:603)
in TetraListCell (created by TetraListCell)
in TetraListCell (at RNInternalSettingsUnit.js:35)
in TetraList (at RNInternalSettingsUnit.js:32)
in RNInternalSettingsUnit (at RNInternalSettingsDeveloperModeUnit.new.js:73)
in RNInternalSettingsDeveloperModeUnit (at RNInternalSettingsSurface.js:79)
in RNInternalSettingsSurface (at withDefaultErrorBoundary.js:30)
in DefaultError(React.lazy(RNInternalSettingsSurfaceForFacebook)) (at renderApplication.js:47)
```
changelog: [internal] internal
Reviewed By: fkgozali
Differential Revision: D25313414
fbshipit-source-id: ab951d25ac6a80809a2977c80ff059f667cc5595
Summary:
I was looking into why CI was failing and could not reproduce locally, also noticed the errors seemed to come from old version of files being used, for example a missing symbol added in a JSI commit ~1 month ago. I noticed that we were using multiple cache keys for a lot of deps in the following format:
```
- v3-pods-{{ .Environment.CIRCLE_JOB }}-{{ checksum "packages/rn-tester/Podfile.lock.bak" }}
- v3-pods-{{ .Environment.CIRCLE_JOB }}-
```
This means that if the cache doesn't exist for the checksum of the lockfile it will get one for any other checksum. This can lead to loading old version of files that cocoapod / yarn probably doesn't detect and keeps instead of getting the proper version. To make things worst it then caches the broken dep package after.
This removes all of these key fallbacks and use the cache only if we have a perfect match. This should make CI more reliable and fix random breaks after updating deps / pod configs.
## Changelog
[Internal] [Fixed] - Make dependencies cache more reliable on CI
Pull Request resolved: https://github.com/facebook/react-native/pull/30534
Test Plan:
- Check that tests now pass when cache is bypassed
- Check that it still passes with cache
- Hope the issue stops happening the next time someone updates deps :)
Reviewed By: fkgozali
Differential Revision: D25326131
Pulled By: hramos
fbshipit-source-id: f21cdfca7b2456ac0edbdcce3f9eb0a828a9b977
Summary:
Hermes being a subspec of ReactCore causes some build issues when RN is included in 2 different targets. It also causes it to include a lot of additional dependencies that it doesn't need. This moves it to a separate podspec loosely based on other specs in ReactCommon.
## Changelog
[iOS] [Fixed] - Move hermes to a separate podspec
Pull Request resolved: https://github.com/facebook/react-native/pull/30478
Test Plan: Test that it builds and run properly in an app
Reviewed By: fkgozali
Differential Revision: D25308237
Pulled By: hramos
fbshipit-source-id: b4cc44ea2b1b854831e881dbbf9a2f30f6704001
Summary: Changelog: [Internal] backout change dispatching main queue before using it
Reviewed By: shergin
Differential Revision: D25319046
fbshipit-source-id: 4f8952e577cfd9033fb2c2248b9b056a0d468b5d
Summary:
Just thought I'd add these instructions so devs don't have to check the docs. Also, it makes iOS match Android with instructions in the configuration files
## Changelog
N/A (in my opinion)
Pull Request resolved: https://github.com/facebook/react-native/pull/30461
Test Plan: N/A (because not a code change)
Reviewed By: hramos
Differential Revision: D25309687
Pulled By: TheSavior
fbshipit-source-id: a1907089b9d2e7fe6f2498ce27129c3ae65f7c9a
Summary:
In very marginal cases, it was possible to set up an animation of the following diffing instructions:
```
REMOVE X from parent Y
DELETE X
```
If your LayoutAnimation configuration had no "delete" config, the DELETE would be executed immediately; the REMOVE was erroneously being categorized as an "update" (now fixed)
which caused the REMOVE to be delayed, but then executed very shortly thereafter. So the order of instructions would become:
```
DELETE X
REMOVE X from parent Y
```
which would crash (or at least fail an assertion) when the REMOVE instruction was processed.
This fixes the issue by ensuring that REMOVEs have a corresponding "delete" config, or they are also executed immediately; unless followed by an INSERT (and any combination of `REMOVE, DELETE, INSERT` in the same frame is not possible).
Changelog: [Internal]
Reviewed By: sammy-SC
Differential Revision: D25292560
fbshipit-source-id: 7ffdd6cbcb43126de07a70c197dfaf1ebff83555